├── .gitignore ├── LICENSE ├── README.MD ├── composer.json └── src ├── Read ├── ChunkReadFilter.php └── ExcelToArray.php └── Write └── ArrayToExcel.php /.gitignore: -------------------------------------------------------------------------------- 1 | *.DS_Store 2 | /vendor 3 | sftp-config.json 4 | /*.php 5 | /.idea 6 | /coverage 7 | /.split 8 | /composer.lock 9 | .php_cs.cache -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | The MIT License (MIT) 2 | Copyright © 2018 3 | 4 | Permission is hereby granted, free of charge, 5 | to any person obtaining a copy of this software and 6 | associated documentation files (the “Software”), 7 | to deal in the Software without restriction, 8 | including without limitation the rights to use, 9 | copy, modify, merge, publish, distribute, sublicense, 10 | and/or sell copies of the Software, 11 | and to permit persons to whom the Software is furnished to do so, 12 | subject to the following conditions: 13 | 14 | The above copyright notice and this permission notice shall 15 | be included in all copies or substantial portions of the Software. 16 | 17 | THE SOFTWARE IS PROVIDED “AS IS”, WITHOUT WARRANTY OF ANY KIND, 18 | EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES 19 | OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. 20 | IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, 21 | DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, 22 | TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH 23 | THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. -------------------------------------------------------------------------------- /README.MD: -------------------------------------------------------------------------------- 1 | 2 | # 已停止维护,建议使用 xlswriter [地址](https://xlswriter-docs.viest.me/) 3 | 4 | 5 | ## Installation 6 | 7 | ```shell 8 | $ composer require "rekkles/easyexcel" -vvv 9 | ``` 10 | 11 | ## Usage 12 | ```php 13 | use EasyExcel\Read\ExcelToArray; 14 | use EasyExcel\Read\ChunkReadFilter; 15 | 16 | //简单获取Excel的数据为Array 17 | $config = ['firstRowAsIndex' => true]; 18 | $getData = new ExcelToArray('/Users/rekkles/code/data.csv',$config); 19 | $getData->load(); 20 | var_dump($getData->getData()); 21 | 22 | //分批获取Excel的数据(防止内存泄漏) 23 | $chunk = new ChunkReadFilter(); 24 | $chunk->setRows(10, 2); 25 | $data = new ExcelToArray('/Users/rekkles/code/data.csv'); 26 | var_dump($data->loadByChunk($chunk)->getData()); 27 | 28 | //写入Excel 生成文件到指定目录 29 | $outObj = new ArrayToExcel(array( 30 | 'fileName' => 'test.csv', //导出的excel的文件的名称 31 | 'sheetTitle' => '11', //每个工作薄的标题 32 | 'creator' => 'rekkles', //创建者 33 | 'writeType' => 'CSV', //输出类型 Excel5 Excel7 CSV 34 | 'path' => ROOT_PATH.'file/', //输出路径 确保有写入权限 35 | )); 36 | $outObj->setFirstRow(array('',1111,2222,3333)) 37 | ->fillData(array( 38 | ['','aaa','bbb','ccc'], 39 | ['','ddd','eee','fff'] 40 | )); 41 | ``` 42 | 43 | ## Documentation 44 | 目前是第一版,功能还在逐渐完善中。 45 | 46 | 代码不是很复杂,针对PHPExcel封装了一部, 47 | 遇到问题可以自行debug,有bug提交PR就更好了! 48 | ## Feature 49 | 1.批量导入、导出 50 | 2.支持更多的文件格式 51 | 52 | ## Donate 53 | 54 | wechat 55 | alipay 56 | 57 | [个人博客](https://rekkles.xyz/) 58 | [个人gitbook](https://gitbook.rekkles.xyz/) 59 | 60 | 61 | 62 | -------------------------------------------------------------------------------- /composer.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "rekkles/easyexcel", 3 | "version": "1.0.0", 4 | "description": "Find A Simple Way To Operate Excel.", 5 | "license": "MIT", 6 | "keywords": [ 7 | "Excel", 8 | "PHPExcel" 9 | ], 10 | "authors": [ 11 | { 12 | "name": "Rekkles", 13 | "email": "yinxiangnet@qq.com" 14 | } 15 | ], 16 | "homepage": "https://github.com/justcodingnobb/EasyExcel", 17 | "require": { 18 | "php":">=5.3.9", 19 | "phpoffice/phpexcel": "^1.8" 20 | }, 21 | "autoload": { 22 | "psr-4": { 23 | "EasyExcel\\": "src/" 24 | } 25 | } 26 | } 27 | -------------------------------------------------------------------------------- /src/Read/ChunkReadFilter.php: -------------------------------------------------------------------------------- 1 | _startRow = $startRow; 19 | $this->_endRow = $startRow + $chunkSize; 20 | } 21 | 22 | public function readCell($column, $row, $worksheetName = '') 23 | { 24 | if (($row == 1) || ($row >= $this->_startRow && $row < $this->_endRow)) { 25 | return true; 26 | } 27 | return false; 28 | } 29 | } -------------------------------------------------------------------------------- /src/Read/ExcelToArray.php: -------------------------------------------------------------------------------- 1 | 'Excel5', 17 | 'xlsx' => 'Excel2007', 18 | 'csv' => 'CSV', 19 | 'xsl' => 'SYLK', 20 | ); 21 | private $firstRow; 22 | private $config; 23 | 24 | /** 25 | * ExcelToArray constructor. 26 | * @param $path 27 | * @throws \Exception 28 | */ 29 | public function __construct($path, $config = array()) 30 | { 31 | $this->path = $path; 32 | $this->config = $config; 33 | $this->fileName = $this->getFileName(); 34 | $this->ext = $this->getExt(); 35 | if (isset($this->fileType[strtolower($this->ext)])) { 36 | $this->readObj = \PHPExcel_IOFactory::createReader($this->fileType[strtolower($this->ext)]); 37 | $this->readObj->setReadDataOnly(true); //只读取数据 38 | } else { 39 | throw new \Exception('File Extension Is Not Illegal'); 40 | } 41 | return $this; 42 | } 43 | 44 | /** 45 | * 获取路径中的文件名 46 | * @return string 47 | */ 48 | private function getFileName() 49 | { 50 | return basename($this->path); 51 | } 52 | 53 | /** 54 | * 获取文件后缀 55 | * 56 | * @return mixed 57 | */ 58 | public function getExt() 59 | { 60 | return pathinfo($this->fileName, PATHINFO_EXTENSION); 61 | } 62 | 63 | /** 64 | * 获取行数 65 | * @return mixed 66 | */ 67 | public function getRowNumber() 68 | { 69 | if (!$this->loadObj) { 70 | $this->load(); 71 | } 72 | return $this->loadObj->getActiveSheet()->getHighestRow(); 73 | } 74 | 75 | /** 76 | * 加载文件到内存 77 | * @return $this 78 | */ 79 | public function load() 80 | { 81 | $this->loadObj = $this->readObj->load($this->path); 82 | return $this; 83 | } 84 | 85 | /** 86 | * 分批加载文件到内存 87 | * @param ChunkReadFilter $chunkReadFilter 88 | * @return $this 89 | */ 90 | public function loadByChunk(ChunkReadFilter $chunkReadFilter) 91 | { 92 | $this->readObj->setReadFilter($chunkReadFilter); 93 | $this->loadObj = $this->readObj->load($this->path); 94 | return $this; 95 | } 96 | 97 | /** 98 | * 切换工作薄 99 | * @param $index 100 | * @return $this 101 | */ 102 | public function setSheet($index) 103 | { 104 | $this->loadObj->setActiveSheetIndex($index); 105 | return $this; 106 | } 107 | 108 | /** 109 | * 获取所有Sheets 110 | * @return mixed 111 | */ 112 | public function getAllSheet() 113 | { 114 | return $this->loadObj->getAllSheets(); 115 | } 116 | 117 | /** 118 | * 获取第一列的字段 119 | * @return mixed 120 | * @throws \PHPExcel_Exception 121 | */ 122 | public function getFirstRow() 123 | { 124 | $loadedWorkSheet = $this->loadObj->getActiveSheet(); //获取当前激活Sheet 125 | $maxRow = $loadedWorkSheet->getHighestRow(); //获取最大行 int 126 | $maxColumn = $loadedWorkSheet->getHighestColumn(); //获取最大列 (A-Z) 127 | $highestColumnIndex = \PHPExcel_Cell::columnIndexFromString($maxColumn); //根据列名获取index 128 | for ($col = 0; $col < $highestColumnIndex; $col++) { 129 | $this->firstRow[] = (string)$loadedWorkSheet->getCellByColumnAndRow($col, 1)->getValue(); 130 | } 131 | return $this->firstRow; 132 | } 133 | 134 | /** 135 | * 获取内容 136 | * @return array 137 | */ 138 | public function getData() 139 | { 140 | $loadedWorkSheet = $this->loadObj->getActiveSheet(); //获取当前激活Sheet 141 | $maxRow = $loadedWorkSheet->getHighestRow(); //获取最大行 int 142 | $maxColumn = $loadedWorkSheet->getHighestColumn(); //获取最大列 (A-Z) 143 | $highestColumnIndex = \PHPExcel_Cell::columnIndexFromString($maxColumn); //根据列名获取index 144 | 145 | //从第二行获取行数据 (第一行是字段) 146 | for ($row = 2; $row <= $maxRow; $row++) { 147 | //从第一列获取列的数据 148 | for ($col = 0; $col < $highestColumnIndex; $col++) { 149 | if (isset($this->config['firstRowAsIndex']) && $this->config['firstRowAsIndex']) { 150 | if (empty($this->firstRow)) { 151 | $this->getFirstRow(); 152 | } 153 | //第一列的字段作key 154 | $this->data[$row - 2][$this->firstRow[$col]] = (string)$loadedWorkSheet->getCellByColumnAndRow($col, $row)->getValue(); 155 | } else { 156 | $this->data[$row - 2][] = (string)$loadedWorkSheet->getCellByColumnAndRow($col, $row)->getValue(); 157 | } 158 | } 159 | } 160 | $this->loadObj->disconnectWorksheets(); 161 | unset($objReader, $objPHPExcel, $objWorkSheet, $highestColumnIndex); 162 | return $this->data; 163 | } 164 | } -------------------------------------------------------------------------------- /src/Write/ArrayToExcel.php: -------------------------------------------------------------------------------- 1 | array(//列的属性设置 10 | 'colName' => '',//第一行的列名 11 | 'keyName' => '',//每一列对应的赋值数组的key值 12 | 'width' => '' //A列的宽度 13 | ) 14 | ); //列属性 15 | private $rowAttr = array( 16 | 'firstRowHeight' => '', //第一行的列名的高度 17 | 'height' => '' //2-OO无从行的高度 18 | ); //行属性 19 | private $options = array( 20 | 'fileName' => '', //导出的excel的文件的名称 21 | 'sheetTitle' => '', //每个工作薄的标题 22 | 'creator' => '', //创建者 23 | 'lastModified' => '', //最近修改时间 24 | 'title' => '', //当前活动的主题 25 | 'subject' => '', 26 | 'description' => '', 27 | 'keywords' => '', 28 | 'category' => '', 29 | 'writeType' => '' //输出类型 Excel5 Excel7 CSV 30 | ); //文件选项 31 | private $validData = array(); //数据有效性 32 | private $colDefaultDefine = array( 33 | 'A', 'B', 'C', 'D', 'E', 'F', 'G', 'H', 'I', 'J', 'K', 'L', 'M', 34 | 'N', 'O', 'P', 'Q', 'R', 'S', 'T', 'U', 'V', 'W', 'X', 'Y', 'Z', 35 | ); //默认列定义 36 | private $writeType = array( 37 | 'excel5' => 'Excel5', 38 | 'excel2007' => 'Excel2007', 39 | 'csv' => 'CSV', 40 | ); //写入文件类型 41 | 42 | public function __construct(array $options) 43 | { 44 | if (!isset($options['fileName'])) { 45 | throw new \Exception('fileName is require'); 46 | } 47 | if (!isset($options['path'])) { 48 | throw new \Exception('path is require'); 49 | } 50 | if (!isset($options['writeType'])) { 51 | throw new \Exception('writeType is require'); 52 | } 53 | 54 | $this->options['writeType'] = $this->writeType[strtolower($options['writeType'])]; 55 | $this->options = $options; 56 | $this->excelObj = new \PHPExcel(); 57 | } 58 | 59 | /** 60 | * 设置Excel第一行表头 一维数组/二维数组 61 | * @param array $col 62 | * @return $this 63 | * @throws \PHPExcel_Exception 64 | */ 65 | public function setFirstRow(array $col) 66 | { 67 | if (empty($col)) { 68 | throw new \Exception('Col is not be Null'); 69 | } 70 | 71 | $this->colAttr = $col; 72 | $obj = $this->excelObj->getActiveSheet(); 73 | 74 | foreach ($col as $key => $val) { 75 | //设置 Vertical 和 Horizontal 76 | $this->excelObj->getActiveSheet() 77 | ->getStyle($key) 78 | ->getAlignment() 79 | ->setVertical(\PHPExcel_Style_Alignment::VERTICAL_CENTER) 80 | ->setHorizontal(\PHPExcel_Style_Alignment::HORIZONTAL_CENTER); 81 | 82 | //设置第一行字段名 83 | $colIndex = !is_array($val) ? $this->colDefaultDefine[$key] : $key; 84 | $colValue = !is_array($val) ? $val : $val['colName']; 85 | $this->excelObj->getActiveSheet()-> 86 | setCellValue($colIndex . '1', $colValue); 87 | 88 | //设置列的宽度 or 跟随字体长度宽度 89 | if (isset($val['width']) && !empty($val['width'])) { 90 | $this->excelObj->getActiveSheet()-> 91 | getColumnDimension($colIndex)->setWidth($val['width']); 92 | } else { 93 | $this->excelObj->getActiveSheet()-> 94 | getColumnDimension($colIndex)->setAutoSize(true); 95 | } 96 | } 97 | 98 | return $this; 99 | } 100 | 101 | public function fillData(array $data, array $valiData = array()) 102 | { 103 | if (isset($this->options['lastModified'])) { 104 | $this->excelObj->getProperties()->setLastModifiedBy($this->options['lastModified']); 105 | } 106 | if (isset($this->options['title'])) { 107 | $this->excelObj->getProperties()->setTitle($this->options['title']); 108 | } 109 | if (isset($this->options['subject'])) { 110 | $this->excelObj->getProperties()->setSubject($this->options['subject']); 111 | } 112 | if (isset($this->options['description'])) { 113 | $this->excelObj->getProperties()->setDescription($this->options['description']); 114 | } 115 | if (isset($this->options['keywords'])) { 116 | $this->excelObj->getProperties()->setKeywords($this->options['keywords']); 117 | } 118 | if (isset($this->options['category'])) { 119 | $this->excelObj->getProperties()->setCategory($this->options['category']); 120 | } 121 | if (isset($this->options['category'])) { 122 | $this->excelObj->getProperties()->setTitle($this->options['category']); 123 | } 124 | 125 | //填充 126 | for ($p = 0; $p < count($data); $p++) { 127 | //行数num,第二行开始 128 | $row = $p + 2; 129 | // 设置数据的有效性 130 | if (isset($valiData) && !empty($valiData)) { 131 | //总分数据有效性下拉菜单 132 | $objValidNum = $this->excelObj->getActiveSheet()->getCell($valiData['list1'][0] . $row)->getDataValidation(); 133 | $objValidNum->setType(\PHPExcel_Cell_DataValidation::TYPE_LIST); 134 | $objValidNum->setErrorStyle(\PHPExcel_Cell_DataValidation::STYLE_INFORMATION); 135 | $objValidNum->setAllowBlank(false); 136 | $objValidNum->setShowInputMessage(true); 137 | $objValidNum->setShowErrorMessage(true); 138 | $objValidNum->setShowDropDown(true); 139 | $objValidNum->setFormula1('"' . $valiData['list1'][1] . '"'); 140 | $objValidNum->getActiveSheet()->getCell('F' . $row)->setDataValidation($objValidation1); 141 | 142 | //学期数据有效性下拉菜单 143 | $objValid = $this->excelObj->getActiveSheet()->getCell($valiData['list2'][0] . $row)->getDataValidation(); 144 | $objValid->setType(\PHPExcel_Cell_DataValidation::TYPE_LIST); 145 | $objValid->setErrorStyle(\PHPExcel_Cell_DataValidation::STYLE_INFORMATION); 146 | $objValid->setAllowBlank(false); 147 | $objValid->setShowInputMessage(true); 148 | $objValid->setShowErrorMessage(true); 149 | $objValid->setShowDropDown(true); 150 | $objValid->setFormula1('"' . $valiData['list2'][1] . '"'); 151 | $this->excelObj->getActiveSheet()->getCell('G' . $row)->setDataValidation($objValidation2); 152 | } 153 | 154 | //填充数据 155 | foreach ($this->colAttr as $colKey => $colVal) { 156 | $colIndex = !is_array($colVal) ? $this->colDefaultDefine[$colKey] : $colKey; 157 | $colVal = !is_array($colVal) ? $colVal : $colVal['colName']; 158 | $this->excelObj->getActiveSheet()->setCellValue($colIndex . $row, $data[$p][$colKey]); 159 | } 160 | 161 | //设置行高 162 | if (isset($this->rowAttr['height']) && !empty($this->rowAttr['height'])) { 163 | $this->excelObj->getActiveSheet()->getRowDimension($row)->setRowHeight($this->rowAttr['height']); 164 | } 165 | } 166 | ob_end_clean(); 167 | ob_start(); 168 | $objWriter = \PHPExcel_IOFactory::createWriter($this->excelObj, $this->options['writeType']); 169 | $objWriter->save($this->options['path'] . $this->options['fileName']);//php://output 170 | } 171 | } 172 | 173 | ?> --------------------------------------------------------------------------------