Conditions | 51 |
Paths | > 20000 |
Total Lines | 473 |
Code Lines | 235 |
Lines | 0 |
Ratio | 0 % |
Changes | 0 |
Small methods make your code easier to understand, in particular if combined with a good name. Besides, if your method is small, finding a good name is usually much easier.
For example, if you find yourself adding comments to a method's body, this is usually a good sign to extract the commented part to a new method, and use the comment as a starting point when coming up with a good name for this new method.
Commonly applied refactorings include:
If many parameters/temporary variables are present:
1 | <?php |
||
772 | public function export() |
||
773 | { |
||
774 | clearstatcache(); |
||
775 | session_write_close(); |
||
776 | |||
777 | # data to send |
||
778 | $data = []; |
||
779 | |||
780 | # environment settings |
||
781 | $post = $this->getPost(); # catch $_POST |
||
782 | $this->setTerminal(true); # set terminal |
||
783 | |||
784 | # TRY-CATCH-BLOCK |
||
785 | try { |
||
786 | |||
787 | # STANDARD VALIDATIONS [check method] |
||
788 | if (!$this->isPost()) |
||
789 | { |
||
790 | $http = new Http(); |
||
791 | $http->writeStatus($http::HTTP_METHOD_NOT_ALLOWED); |
||
792 | |||
793 | die('Error ' . $http::HTTP_METHOD_NOT_ALLOWED .' (' . $http->getStatusText($http::HTTP_METHOD_NOT_ALLOWED) . ')!!'); |
||
794 | } |
||
795 | |||
796 | # STANDARD VALIDATIONS [check needed arguments] |
||
797 | $needles = ['conn', 'sql', 'type', 'filename']; |
||
798 | |||
799 | array_walk($needles, function(&$item) use ($post) { |
||
800 | if (!array_key_exists($item, $post)) |
||
801 | { |
||
802 | $http = new Http(); |
||
803 | $http->writeStatus($http::HTTP_BAD_REQUEST); |
||
804 | |||
805 | die('Error ' . $http::HTTP_BAD_REQUEST .' (' . $http->getStatusText($http::HTTP_BAD_REQUEST) . ')!!'); |
||
806 | } |
||
807 | }); |
||
808 | |||
809 | $components = [ |
||
810 | "attributes" => [ |
||
811 | "conn" => [ |
||
812 | "required" => true, |
||
813 | "type" => "number" |
||
814 | ], |
||
815 | "sql" => [ |
||
816 | "required" => true, |
||
817 | "type" => "text" |
||
818 | ], |
||
819 | "type" => [ |
||
820 | "required" => true, |
||
821 | "type" => "text" |
||
822 | ], |
||
823 | "filename" => [ |
||
824 | "required" => true, |
||
825 | "type" => "text" |
||
826 | ] |
||
827 | ], |
||
828 | ]; |
||
829 | |||
830 | $options = [ |
||
831 | "conn" => [ |
||
832 | "label" => "Connection", |
||
833 | ], |
||
834 | "sql" => [ |
||
835 | "label" => "SQL", |
||
836 | "validators" => [ |
||
837 | "Regex" => ["pattern" => '/^[a-zA-Z0-9\+\/]+$/'] |
||
838 | ] |
||
839 | ], |
||
840 | "type" => [ |
||
841 | "label" => "Type", |
||
842 | "validators" => [ |
||
843 | "InArray" => ["haystack" => ['excel', 'csv']] |
||
844 | ] |
||
845 | ], |
||
846 | "filename" => [ |
||
847 | "label" => "Filename" |
||
848 | ] |
||
849 | ]; |
||
850 | |||
851 | $form = new Form($components); |
||
852 | $form->fill($post); |
||
853 | |||
854 | $validator = new FormValidator($form, $options); |
||
855 | $validator->validate(); |
||
856 | |||
857 | $data["validator"] = $validator; |
||
858 | |||
859 | # form validation |
||
860 | if (!$validator->isValid()) |
||
861 | { |
||
862 | $data["messages"] = $validator->getMessages(); |
||
863 | throw new \Drone\Exception\Exception("Form validation errors", 300); |
||
864 | } |
||
865 | |||
866 | $id = $post["conn"]; |
||
867 | |||
868 | $connection = $this->getUserConnectionEntity()->select([ |
||
869 | "USER_CONN_ID" => $id |
||
870 | ]); |
||
871 | |||
872 | if (!count($connection)) |
||
873 | throw new \Exception("The Connection does not exists"); |
||
874 | |||
875 | $connection = array_shift($connection); |
||
876 | |||
877 | if ($connection->STATE == 'I') |
||
878 | throw new \Drone\Exception\Exception("This connection was deleted", 300); |
||
879 | |||
880 | $details = $this->getUserConnectionDetailsEntity()->select([ |
||
881 | "USER_CONN_ID" => $id |
||
882 | ]); |
||
883 | |||
884 | $idenfiers = $this->getIdentifiersEntity()->select([]); |
||
885 | |||
886 | $dbconfig = []; |
||
887 | |||
888 | foreach ($details as $field) |
||
889 | { |
||
890 | foreach ($idenfiers as $identifier) |
||
891 | { |
||
892 | if ($field->CONN_IDENTI_ID == $identifier->CONN_IDENTI_ID) |
||
893 | $dbconfig[$identifier->CONN_IDENTI_NAME] = $field->FIELD_VALUE; |
||
894 | } |
||
895 | } |
||
896 | |||
897 | /* sql post value muest be ever base64 encoded */ |
||
898 | $post["sql"] = base64_decode($post["sql"]); |
||
899 | $data["sql"] = $post["sql"]; |
||
900 | |||
901 | $sql_text = $post["sql"]; |
||
902 | |||
903 | /* |
||
904 | * SQL parsing |
||
905 | */ |
||
906 | $sql_text = trim($sql_text); |
||
907 | |||
908 | if (empty($sql_text)) |
||
909 | throw new \Drone\Exception\Exception("Empty statement"); |
||
910 | |||
911 | $pos = strpos($sql_text, ';'); |
||
912 | |||
913 | if ($pos !== false) |
||
914 | { |
||
915 | $end_stament = strstr($sql_text, ';'); |
||
916 | |||
917 | if ($end_stament == ';') |
||
918 | $sql_text = strstr($sql_text, ';', true); |
||
919 | } |
||
920 | |||
921 | # clean comments and other characters |
||
922 | |||
923 | // (/**/) |
||
924 | $clean_code = preg_replace('/(\s)*\/\*([^*]|[\r\n]|(\*+([^*\/]|[\r\n])))*\*+\//', '', $sql_text); |
||
925 | |||
926 | // (--) |
||
927 | $clean_code = preg_replace('/(\s)*--.*\n/', "", $clean_code); |
||
928 | |||
929 | # clean other characters starting senteces |
||
930 | $clean_code = preg_replace('/^[\n\t\s]*/', "", $clean_code); |
||
931 | |||
932 | # indicates if SQL is a selection statement |
||
933 | $isSelectStm = $data["selectStm"] = (preg_match('/^SELECT/i', $clean_code)); |
||
934 | |||
935 | # indicates if SQL is a show statement |
||
936 | $isShowStm = $data["showStm"] = (preg_match('/^SHOW/i', $clean_code)); |
||
937 | |||
938 | # detect selection |
||
939 | if (!$isSelectStm && !$isShowStm) |
||
940 | throw new \Exception("You can't export a non-selection statement!"); |
||
941 | |||
942 | try { |
||
943 | |||
944 | $connError = false; |
||
945 | |||
946 | $entity = new EntityMd([]); |
||
947 | $entity->setConnectionIdentifier("CONN" . $id); |
||
948 | |||
949 | $driverAdapter = new \Drone\Db\Driver\DriverAdapter($dbconfig, false); |
||
950 | |||
951 | # start time to compute execution |
||
952 | $startTime = microtime(true); |
||
953 | |||
954 | $driverAdapter->getDb()->connect(); |
||
955 | |||
956 | $auth = $driverAdapter; |
||
957 | |||
958 | $data["results"] = $auth->getDb()->execute($sql_text); |
||
959 | } |
||
960 | # encapsulate real connection error! |
||
961 | catch (\Drone\Db\Driver\Exception\ConnectionException $e) |
||
962 | { |
||
963 | $connError = true; |
||
964 | |||
965 | $file = str_replace('\\', '', __CLASS__); |
||
966 | $storage = new \Drone\Exception\Storage("cache/$file.json"); |
||
967 | |||
968 | # stores the error code |
||
969 | if (($errorCode = $storage->store($e)) === false) |
||
970 | { |
||
971 | $errors = $storage->getErrors(); |
||
972 | |||
973 | # if error storing is not possible, handle it (internal app error) |
||
974 | $this->handleErrors($errors, __METHOD__); |
||
975 | } |
||
976 | |||
977 | $data["code"] = $errorCode; |
||
978 | $data["message"] = "Could not connect to database"; |
||
979 | |||
980 | # to identify development mode |
||
981 | $config = include 'config/application.config.php'; |
||
982 | $data["dev_mode"] = $config["environment"]["dev_mode"]; |
||
983 | |||
984 | # redirect view |
||
985 | $this->setMethod('error'); |
||
986 | } |
||
987 | catch (\Exception $e) |
||
988 | { |
||
989 | # SUCCESS-MESSAGE |
||
990 | $data["process"] = "error"; |
||
991 | $data["message"] = $e->getMessage(); |
||
992 | |||
993 | return $data; |
||
994 | } |
||
995 | |||
996 | # end time to compute execution |
||
997 | $endTime = microtime(true); |
||
998 | $elapsed_time = $endTime - $startTime; |
||
999 | |||
1000 | $data["time"] = round($elapsed_time, 4); |
||
1001 | |||
1002 | if (!$connError) |
||
1003 | { |
||
1004 | $data["num_rows"] = $auth->getDb()->getNumRows(); |
||
1005 | $data["num_fields"] = $auth->getDb()->getNumFields(); |
||
1006 | $data["rows_affected"] = $auth->getDb()->getRowsAffected(); |
||
1007 | |||
1008 | $rows = $auth->getDb()->getArrayResult(); |
||
1009 | |||
1010 | # columns with errors in a select statement |
||
1011 | $column_errors = []; |
||
1012 | |||
1013 | switch ($post["type"]) |
||
1014 | { |
||
1015 | case 'excel': |
||
1016 | $ext = '.xls'; |
||
1017 | break; |
||
1018 | case 'csv': |
||
1019 | $ext = '.csv'; |
||
1020 | break; |
||
1021 | default: |
||
1022 | $ext = '.txt'; |
||
1023 | break; |
||
1024 | } |
||
1025 | |||
1026 | $filename = $post["filename"] . $ext; |
||
1027 | |||
1028 | $file_hd = @fopen("cache/" . $filename, "w+"); |
||
1029 | |||
1030 | if (!$file_hd) |
||
1031 | { |
||
1032 | $this->error(Errno::FILE_PERMISSION_DENIED, "cache/" . $filename); |
||
1033 | throw new \Exception("The file could not be created!"); |
||
1034 | } |
||
1035 | |||
1036 | $contents = ""; |
||
1037 | |||
1038 | $data["data"] = []; |
||
1039 | |||
1040 | switch ($post["type"]) |
||
1041 | { |
||
1042 | case 'excel': |
||
1043 | |||
1044 | $table = "<html xmlns:v='urn:schemas-microsoft-com:vml' \r\n\txmlns:o='urn:schemas-microsoft-com:office:office'\r\n"; |
||
1045 | $table .= "\txmlns:x='urn:schemas-microsoft-com:office:excel'\r\n"; |
||
1046 | $table .= "\txmlns='http://www.w3.org/TR/REC-html40'>\r\n"; |
||
1047 | |||
1048 | $table .= "<head>\r\n"; |
||
1049 | $table .= "\t<meta name='Excel Workbook Frameset'><meta http-equiv='Content-Type' content='text/html; charset='utf-8'>\r\n"; |
||
1050 | $table .= "</head>\r\n\r\n"; |
||
1051 | |||
1052 | $table .= "<body>\r\n<table border=1>\r\n"; |
||
1053 | |||
1054 | $column_names = []; |
||
1055 | |||
1056 | foreach ($rows[0] as $column_name => $row) |
||
1057 | { |
||
1058 | if (!is_numeric($column_name)) |
||
1059 | $column_names[] = $column_name; |
||
1060 | } |
||
1061 | |||
1062 | $table .= "\t<thead>\r\n\t\t<tr>\r\n"; |
||
1063 | |||
1064 | foreach ($column_names as $column_name) |
||
1065 | { |
||
1066 | $table .= "\t\t\t<th>$column_name</th>\r\n"; |
||
1067 | } |
||
1068 | |||
1069 | $table .= "\t\t</tr>\r\n\t</thead>\r\n\t<tbody>"; |
||
1070 | |||
1071 | # data parsing |
||
1072 | foreach ($rows as $key => $row) |
||
1073 | { |
||
1074 | $data["data"][$key] = []; |
||
1075 | |||
1076 | foreach ($row as $column => $value) |
||
1077 | { |
||
1078 | if ($isShowStm) |
||
1079 | $column++; |
||
1080 | |||
1081 | if (gettype($value) == 'object') |
||
1082 | { |
||
1083 | if (get_class($value) == 'OCI-Lob') |
||
1084 | { |
||
1085 | if (($val = @$value->load()) === false) |
||
1086 | { |
||
1087 | $val = null; # only for default, this value is not used |
||
1088 | $column_errors[] = $column; |
||
1089 | } |
||
1090 | |||
1091 | $data["data"][$key][$column] = $val; |
||
1092 | } |
||
1093 | else |
||
1094 | $data["data"][$key][$column] = $value; |
||
1095 | } |
||
1096 | else { |
||
1097 | $data["data"][$key][$column] = $value; |
||
1098 | } |
||
1099 | } |
||
1100 | |||
1101 | } |
||
1102 | |||
1103 | foreach ($data["data"] as $row) |
||
1104 | { |
||
1105 | $table .= "\t\t<tr>\r\n"; |
||
1106 | |||
1107 | foreach ($column_names as $column_name) |
||
1108 | { |
||
1109 | $table .= "\t\t\t<td>". $row[$column_name] ."</td>\r\n"; |
||
1110 | } |
||
1111 | |||
1112 | $table .= "\t\t</tr>\r\n"; |
||
1113 | } |
||
1114 | |||
1115 | $table .= "\t</tbody>\r\n</table>\r\n</body>\r\n</html>"; |
||
1116 | $contents = $table; |
||
1117 | |||
1118 | break; |
||
1119 | |||
1120 | case 'csv': |
||
1121 | |||
1122 | $text = ""; |
||
1123 | |||
1124 | $column_names = []; |
||
1125 | |||
1126 | foreach ($rows[0] as $column_name => $row) |
||
1127 | { |
||
1128 | if (!is_numeric($column_name)) |
||
1129 | $column_names[] = $column_name; |
||
1130 | } |
||
1131 | |||
1132 | foreach ($column_names as $column_name) |
||
1133 | { |
||
1134 | $text .= "$column_name;"; |
||
1135 | } |
||
1136 | |||
1137 | $text .= "\r\n"; |
||
1138 | |||
1139 | # data parsing |
||
1140 | foreach ($rows as $key => $row) |
||
1141 | { |
||
1142 | $data["data"][$key] = []; |
||
1143 | |||
1144 | foreach ($row as $column => $value) |
||
1145 | { |
||
1146 | if ($isShowStm) |
||
1147 | $column++; |
||
1148 | |||
1149 | if (gettype($value) == 'object') |
||
1150 | { |
||
1151 | if (get_class($value) == 'OCI-Lob') |
||
1152 | { |
||
1153 | if (($val = @$value->load()) === false) |
||
1154 | { |
||
1155 | $val = null; # only for default, this value is not used |
||
1156 | $column_errors[] = $column; |
||
1157 | } |
||
1158 | |||
1159 | $data["data"][$key][$column] = $val; |
||
1160 | } |
||
1161 | else |
||
1162 | $data["data"][$key][$column] = $value; |
||
1163 | } |
||
1164 | else { |
||
1165 | $data["data"][$key][$column] = $value; |
||
1166 | } |
||
1167 | } |
||
1168 | } |
||
1169 | |||
1170 | foreach ($data["data"] as $row) |
||
1171 | { |
||
1172 | foreach ($column_names as $column_name) |
||
1173 | { |
||
1174 | $text .= $row[$column_name] . ";"; |
||
1175 | } |
||
1176 | |||
1177 | $text .= "\r\n"; |
||
1178 | } |
||
1179 | |||
1180 | $contents = $text; |
||
1181 | |||
1182 | break; |
||
1183 | |||
1184 | default: |
||
1185 | # code... |
||
1186 | break; |
||
1187 | } |
||
1188 | |||
1189 | if (!@fwrite($file_hd, $contents)) |
||
1190 | { |
||
1191 | $this->error(Errno::FILE_PERMISSION_DENIED, "cache/" . $filename); |
||
1192 | throw new \Exception("The file could not be generated!"); |
||
1193 | } |
||
1194 | |||
1195 | @fclose($file_hd); |
||
1196 | |||
1197 | $data["column_errors"] = $column_errors; |
||
1198 | |||
1199 | $data["filename"] = $filename; |
||
1200 | |||
1201 | if (array_key_exists('id', $post)) |
||
1202 | $data["id"] = $post["id"]; |
||
1203 | |||
1204 | # SUCCESS-MESSAGE |
||
1205 | $data["process"] = "success"; |
||
1206 | } |
||
1207 | } |
||
1208 | catch (\Drone\Exception\Exception $e) |
||
1209 | { |
||
1210 | # ERROR-MESSAGE |
||
1211 | $data["process"] = "warning"; |
||
1212 | $data["message"] = $e->getMessage(); |
||
1213 | } |
||
1214 | catch (\Exception $e) |
||
1215 | { |
||
1216 | $file = str_replace('\\', '', __CLASS__); |
||
1217 | $storage = new \Drone\Exception\Storage("cache/$file.json"); |
||
1218 | |||
1219 | # stores the error code |
||
1220 | if (($errorCode = $storage->store($e)) === false) |
||
1221 | { |
||
1222 | $errors = $storage->getErrors(); |
||
1223 | |||
1224 | # if error storing is not possible, handle it (internal app error) |
||
1225 | $this->handleErrors($errors, __METHOD__); |
||
1226 | } |
||
1227 | |||
1228 | # errors retrived by the use of ErrorTrait |
||
1229 | if (count($this->getErrors())) |
||
1230 | $this->handleErrors($this->getErrors(), __METHOD__); |
||
1231 | |||
1232 | $data["code"] = $errorCode; |
||
1233 | $data["message"] = $e->getMessage(); |
||
1234 | |||
1235 | $config = include 'config/application.config.php'; |
||
1236 | $data["dev_mode"] = $config["environment"]["dev_mode"]; |
||
1237 | |||
1238 | # redirect view |
||
1239 | $this->setMethod('error'); |
||
1240 | |||
1241 | return $data; |
||
1242 | } |
||
1243 | |||
1244 | return $data; |
||
1245 | } |
||
1277 | } |