ajax.csvimport.php 7.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230
  1. <?php
  2. require_once('../application/application.inc.php');
  3. require_once('../application/webpage.class.inc.php');
  4. require_once('../application/ajaxwebpage.class.inc.php');
  5. require_once('../application/wizardhelper.class.inc.php');
  6. require_once('../application/ui.linkswidget.class.inc.php');
  7. require_once('../application/csvpage.class.inc.php');
  8. /**
  9. * Helper function to build the mapping drop-down list for a field
  10. */
  11. function GetMappingForField($sClassName, $sFieldName, $iFieldIndex)
  12. {
  13. $aChoices = array('' => '-- select one --');
  14. $aChoices[':none:'] = '------ n/a ------';
  15. $aChoices['id'] = 'id (Primary Key)';
  16. foreach(MetaModel::ListAttributeDefs($sClassName) as $sAttCode => $oAttDef)
  17. {
  18. if ($oAttDef->IsExternalKey())
  19. {
  20. $aChoices[$sAttCode] = $oAttDef->GetLabel();
  21. // Get fields of the external class that are considered as reconciliation keys
  22. $sTargetClass = $oAttDef->GetTargetClass();
  23. foreach(MetaModel::ListAttributeDefs($sTargetClass) as $sTargetAttCode => $oTargetAttDef)
  24. {
  25. if (MetaModel::IsReconcKey($sTargetClass, $sTargetAttCode))
  26. {
  27. $aChoices[$sAttCode.'->'.$sTargetAttCode] = $oAttDef->GetLabel().'->'.$oTargetAttDef->GetLabel();
  28. }
  29. }
  30. }
  31. else if ($oAttDef->IsWritable())
  32. {
  33. $aChoices[$sAttCode] = $oAttDef->GetLabel();
  34. }
  35. }
  36. asort($aChoices);
  37. $sHtml = "<select id=\"mapping_{$iFieldIndex}\" name=\"field[$iFieldIndex]\">\n";
  38. foreach($aChoices as $sAttCode => $sLabel)
  39. {
  40. $sSelected = '';
  41. if ( ($sFieldName == $sAttCode) || ($sFieldName == $sLabel))
  42. {
  43. $sSelected = ' selected';
  44. }
  45. $sHtml .= "<option value=\"$sAttCode\"$sSelected>$sLabel</option>\n";
  46. }
  47. $sHtml .= "</select>\n";
  48. return $sHtml;
  49. }
  50. require_once('../application/startup.inc.php');
  51. session_start();
  52. if (isset($_SESSION['auth_user']))
  53. {
  54. $sAuthUser = $_SESSION['auth_user'];
  55. $sAuthPwd = $_SESSION['auth_pwd'];
  56. // Attempt to login, fails silently
  57. UserRights::Login($sAuthUser, $sAuthPwd);
  58. }
  59. else
  60. {
  61. // No session information
  62. echo "<p>No session information</p>\n";
  63. }
  64. $oContext = new UserContext();
  65. $sOperation = utils::ReadParam('operation', '');
  66. switch($sOperation)
  67. {
  68. case 'parser_preview':
  69. $oPage = new ajax_page("");
  70. $oPage->no_cache();
  71. $sSeparator = utils::ReadParam('separator', ',');
  72. if ($sSeparator == 'tab') $sSeparator = "\t";
  73. $sTextQualifier = utils::ReadParam('qualifier', '"');
  74. $iLinesToSkip = utils::ReadParam('nb_lines_skipped', 0);
  75. $bFirstLineAsHeader = utils::ReadParam('header_line', true);
  76. $sData = stripslashes(utils::ReadParam('csvdata', true));
  77. $oCSVParser = new CSVParser($sData, $sSeparator, $sTextQualifier);
  78. $aData = $oCSVParser->ToArray($iLinesToSkip);
  79. $iTarget = count($aData);
  80. if ($iTarget == 0)
  81. {
  82. $oPage->p("Empty data set..., please provide some data!");
  83. }
  84. else
  85. {
  86. $sMaxLen = (strlen(''.$iTarget) < 3) ? 3 : strlen(''.$iTarget); // Pad line numbers to the appropriate number of chars, but at least 3
  87. $sFormat = '%0'.$sMaxLen.'d';
  88. $oPage->p("<h3>Data Preview</h3>\n");
  89. $oPage->p("<div style=\"overflow-y:auto\">\n");
  90. $oPage->add("<table cellspacing=\"0\" style=\"overflow-y:auto\">");
  91. $iMaxIndex= 10; // Display maximum 10 lines for the preview
  92. $index = 1;
  93. foreach($aData as $aRow)
  94. {
  95. $sCSSClass = 'csv_row'.($index % 2);
  96. if ( ($bFirstLineAsHeader) && ($index == 1))
  97. {
  98. $oPage->add("<tr class=\"$sCSSClass\"><td style=\"border-left:#999 3px solid;padding-right:10px;padding-left:10px;\">".sprintf($sFormat, $index)."</td><th>");
  99. $oPage->add(implode('</th><th>', $aRow));
  100. $oPage->add("</th></tr>\n");
  101. $iNbCols = count($aRow);
  102. }
  103. else
  104. {
  105. if ($index == 1) $iNbCols = count($aRow);
  106. $oPage->add("<tr class=\"$sCSSClass\"><td style=\"border-left:#999 3px solid;padding-right:10px;padding-left:10px;\">".sprintf($sFormat, $index)."</td><td>");
  107. $oPage->add(implode('</td><td>', $aRow));
  108. $oPage->add("</td></tr>\n");
  109. }
  110. $index++;
  111. if ($index > $iMaxIndex) break;
  112. }
  113. $oPage->add("</table>\n");
  114. $oPage->add("</div>\n");
  115. if($iNbCols == 1)
  116. {
  117. $oPage->p('<img src="../images/error.png">&nbsp;Error: The data contains only one column. Did you select the appropriate separator character ?');
  118. }
  119. else
  120. {
  121. $oPage->p('&nbsp;');
  122. }
  123. }
  124. break;
  125. case 'display_mapping_form':
  126. $oPage = new ajax_page("");
  127. $oPage->no_cache();
  128. $sSeparator = utils::ReadParam('separator', ',');
  129. $sTextQualifier = utils::ReadParam('qualifier', '"');
  130. $iLinesToSkip = utils::ReadParam('nb_lines_skipped', 0);
  131. $bFirstLineAsHeader = utils::ReadParam('header_line', true);
  132. $sData = stripslashes(utils::ReadParam('csvdata', true));
  133. $sClassName = utils::ReadParam('class_name', '');
  134. $oCSVParser = new CSVParser($sData, $sSeparator, $sTextQualifier);
  135. $aData = $oCSVParser->ToArray($iLinesToSkip);
  136. $iTarget = count($aData);
  137. if ($iTarget == 0)
  138. {
  139. $oPage->p("Empty data set..., please provide some data!");
  140. }
  141. else
  142. {
  143. $oPage->add("<table>");
  144. $index = 1;
  145. $aFirstLine = $aData[0]; // Use the first row to determine the number of columns
  146. $iStartLine = 0;
  147. $iNbColumns = count($aFirstLine);
  148. if ($bFirstLineAsHeader)
  149. { $iStartLine = 1;
  150. foreach($aFirstLine as $sField)
  151. {
  152. $aHeader[] = $sField;
  153. }
  154. }
  155. else
  156. {
  157. // Build some conventional name for the fields: field1...fieldn
  158. $index= 1;
  159. foreach($aFirstLine as $sField)
  160. {
  161. $aHeader[] = 'Field'+$index;
  162. $index++;
  163. }
  164. }
  165. $oPage->add("<table>\n");
  166. $oPage->add('<tr>');
  167. $oPage->add("<th>Fields</th><th>Mapping</th><th>&nbsp;</th><th>Search ?</th><th>Data line 1</th><th>Data line 2</th>");
  168. $oPage->add('</tr>');
  169. foreach($aHeader as $sField)
  170. {
  171. $oPage->add('<tr>');
  172. $oPage->add("<th>$sField</th>");
  173. $oPage->add('<td>'.GetMappingForField($sClassName, $sField, $index).'</td>');
  174. $oPage->add('<td>&nbsp;</td>');
  175. $oPage->add('<td><input id="search_'.$index.'" type="checkbox" name="search_field['.$index.']" value="1" /></td>');
  176. $oPage->add('<td>'.(isset($aData[$iStartLine][$index-1]) ? htmlentities($aData[$iStartLine][$index-1], ENT_QUOTES, 'UTF-8') : '&nbsp;').'</td>');
  177. $oPage->add('<td>'.(isset($aData[$iStartLine+1][$index-1]) ? htmlentities($aData[$iStartLine+1][$index-1], ENT_QUOTES, 'UTF-8') : '&nbsp;').'</td>');
  178. $oPage->add('</tr>');
  179. $index++;
  180. }
  181. $oPage->add("</table>\n");
  182. }
  183. break;
  184. case 'get_csv_template':
  185. $sClassName = utils::ReadParam('class_name');
  186. $oSearch = new DBObjectSearch($sClassName);
  187. $oSearch->AddCondition('id', 0); // Make sure we create an empty set
  188. $oSet = new CMDBObjectSet($oSearch);
  189. $sResult = cmdbAbstractObject::GetSetAsCSV($oSet);
  190. //$aCSV = explode("\n", $sCSV);
  191. // If there are more than one line, let's assume that the first line is a comment and skip it.
  192. //if (count($aCSV) > 1)
  193. //{
  194. // $sResult = $aCSV[0];
  195. //}
  196. //else
  197. //{
  198. // $sResult = $sCSV;
  199. //}
  200. $sClassDisplayName = MetaModel::GetName($sClassName);
  201. $sDisposition = utils::ReadParam('disposition', 'inline');
  202. if ($sDisposition == 'attachment')
  203. {
  204. $oPage = new CSVPage("");
  205. $oPage->add_header("Content-disposition: attachment; filename=\"{$sClassDisplayName}.csv\"");
  206. $oPage->no_cache();
  207. $oPage->add($sResult);
  208. }
  209. else
  210. {
  211. $oPage = new ajax_page("");
  212. $oPage->no_cache();
  213. $oPage->add('<p style="text-align:center"><a style="text-decoration:none" href="../pages/ajax.csvimport.php?operation=get_csv_template&disposition=attachment&class_name='.$sClassName.'"><img border="0" src="../images/csv.png"><br/>'.$sClassDisplayName.'.csv</a></p>');
  214. $oPage->add('<p><textarea rows="5" cols="100">'.$sResult.'</textarea></p>');
  215. }
  216. break;
  217. }
  218. $oPage->output();
  219. ?>