namespace App\Models;
+use Cubist\Util\PHP;
+use PhpOffice\PhpSpreadsheet\Cell\Coordinate;
+use PhpOffice\PhpSpreadsheet\Reader\Xlsx;
+use PhpOffice\PhpSpreadsheet\Style\Fill;
+use PhpOffice\PhpSpreadsheet\Style\NumberFormat;
+use PhpOffice\PhpSpreadsheet\Worksheet\Worksheet;
use Symfony\Component\HttpFoundation\File\UploadedFile;
class FeedbackProcess
public function process()
{
- dd($this);
+ PHP::neverStop(false);
+ // Open feedbacks
+ $feedbackSheets = [];
+ foreach ($this->getFeedbacks() as $feedback) {
+ $reader = new Xlsx();
+ $xlsx = $reader->load($feedback);
+ foreach ($xlsx->getAllSheets() as $sheet) {
+ if ($sheet->getSheetState() !== Worksheet::SHEETSTATE_VISIBLE) {
+ continue;
+ }
+ $name = $this->_getSheetName($sheet);
+ if (!isset($feedbackSheets[$name])) {
+ $feedbackSheets[$name] = [];
+ }
+ $feedbackSheets[$name][] = $sheet;
+ }
+ }
+
+ $reader = new Xlsx();
+ $template = $reader->load($this->getTemplate());
+ foreach ($template->getAllSheets() as $sheet) {
+ if ($sheet->getSheetState() !== Worksheet::SHEETSTATE_VISIBLE) {
+ continue;
+ }
+ $name = $this->_getSheetName($sheet);
+ $this->_processSheet($sheet, $feedbackSheets[$name] ?? []);
+ }
+ // Make first sheet active
+ $template->setActiveSheetIndex(0);
+ return $template;
+ }
+
+ /**
+ * @param $sheet Worksheet
+ */
+ protected function _getSheetName($sheet)
+ {
+ return mb_strtolower(trim($sheet->getCellByColumnAndRow(1, 1)->getValue()));
+ }
+
+ /**
+ * @param $templateSheet Worksheet
+ * @param $feedbacks Worksheet[]
+ * @throws \PhpOffice\PhpSpreadsheet\Exception
+ */
+ protected function _processSheet($templateSheet, $feedbacks)
+ {
+ // Find header row
+ $highestRow = $templateSheet->getHighestRow();
+ for ($i = 1; $i <= $highestRow; $i++) {
+ if ($templateSheet->getCellByColumnAndRow(1, $i)->getValue() === 'Picture References') {
+ $headersRow = $i;
+ break;
+ }
+ }
+
+ // Add ranking column
+ $templateSheet->insertNewColumnBefore('O', 1);
+ $h = $templateSheet->getCell('O' . $headersRow);
+ // Style it
+ $h->getStyle()->getFill()->setFillType(Fill::FILL_SOLID)
+ ->getStartColor()
+ ->setARGB('5eba7d');
+ // Set the caption
+ $h->setValue('Rank');
+
+ // Get data from feedbacks
+
+ $startCol = 15;
+ $eanCol = 4;
+ $merged = [];
+ $feedbackId = 0;
+ foreach ($feedbacks as $feedback) {
+ $maxcol = Coordinate::columnIndexFromString($feedback->getHighestColumn());
+ $maxrow = $feedback->getHighestRow();
+ for ($j = $headersRow + 1; $j <= $maxrow; $j++) {
+ $ean = trim($feedback->getCellByColumnAndRow($eanCol, $j)->getValue());
+ if (!isset($merged[$ean])) {
+ $merged[$ean] = [];
+ }
+ for ($i = $startCol; $i <= $maxcol; $i++) {
+ $v = $feedback->getCellByColumnAndRow($i, $j)->getValue();
+ if (null === $v) {
+ continue;
+ }
+ $v = trim($v);
+ if (!$v) {
+ continue;
+ }
+ $merged[$ean][$i - $startCol] = $v;
+ }
+ }
+ }
+ $rankingData = [];
+ // Put feedbacks is template
+ foreach ($merged as $ean => $data) {
+ // Search line by ean
+ $row = null;
+ for ($i = $headersRow + 1; $i <= $highestRow; $i++) {
+ if (trim($templateSheet->getCellByColumnAndRow($eanCol, $i)->getValue()) == $ean) {
+ $row = $i;
+ break;
+ }
+ }
+ if (null === $row) {
+ continue;
+ }
+ $rankingData[$row] = [];
+ // Put data on that row
+ foreach ($data as $col => $value) {
+ // Set the value
+ $templateSheet->setCellValueByColumnAndRow($startCol + 1 + $col, $row, $value);
+ // Gather data to make the ranking
+ if ($col % 4 === 0) {
+ $k = count($rankingData[$row]);
+ $rankingData[$row][$k] = (mb_strtoupper($value) === 'YES' ? 'Y' : 'N');
+ } else if ($col % 2 === 0) {
+ $rankingData[$row][$k] .= (mb_strtoupper($value) ?? 'C');
+ }
+ }
+ }
+
+ $coefs = [
+ 'YA' => 100000,
+ 'YB' => 10000,
+ 'YC' => 1000,
+ 'NA' => 100,
+ 'NB' => 10,
+ 'NC' => 1];
+
+ $scores = [];
+ foreach ($rankingData as $row => $data) {
+ $scores[$row] = 0;
+ foreach ($data as $rank) {
+ $s = $coefs[$rank] ?? 0;
+ $scores[$row] += $s;
+ }
+ }
+ arsort($scores);
+ $rank = 1;
+ foreach ($scores as $row => $score) {
+ $templateSheet->setCellValueByColumnAndRow($startCol, $row, $rank);
+ $templateSheet->getStyleByColumnAndRow($startCol, $row)->getNumberFormat()->setFormatCode(NumberFormat::FORMAT_NUMBER);
+ $rank++;
+ }
+
}
}
"Read more about it at https://getcomposer.org/doc/01-basic-usage.md#installing-dependencies",
"This file is @generated automatically"
],
- "content-hash": "1732cf80b63526e49045d08cadf62e79",
+ "content-hash": "bfd96ac93a06e647207931391a023f90",
"packages": [
{
"name": "asm89/stack-cors",
],
"time": "2021-01-20T22:51:39+00:00"
},
+ {
+ "name": "cubist/net",
+ "version": "dev-master",
+ "source": {
+ "type": "git",
+ "url": "git://git.cubedesigners.com/cubist_net.git",
+ "reference": "4e815d62a6f868789ecce6bdcb9f0a81ddffc64a"
+ },
+ "dist": {
+ "type": "tar",
+ "url": "https://composer.cubedesigners.com/dist/cubist/net/cubist-net-dev-master-28d1c1.tar",
+ "reference": "4e815d62a6f868789ecce6bdcb9f0a81ddffc64a",
+ "shasum": "05f377a7717110e79d264b30738265441d4d9106"
+ },
+ "require": {
+ "ext-ssh2": "*",
+ "php": ">=5.4.0"
+ },
+ "type": "library",
+ "autoload": {
+ "psr-4": {
+ "Cubist\\Net\\": "src"
+ }
+ },
+ "license": [
+ "proprietary"
+ ],
+ "authors": [
+ {
+ "name": "Vincent Vanwaelscappel",
+ "email": "vincent@cubedesigners.com"
+ }
+ ],
+ "description": "net cubist composer package",
+ "time": "2020-12-03T12:49:18+00:00"
+ },
+ {
+ "name": "cubist/util",
+ "version": "dev-master",
+ "source": {
+ "type": "git",
+ "url": "git://git.cubedesigners.com/cubist_util.git",
+ "reference": "4c5cd619a89e6679fca80ff84036f68c554426a7"
+ },
+ "dist": {
+ "type": "tar",
+ "url": "https://composer.cubedesigners.com/dist/cubist/util/cubist-util-dev-master-906685.tar",
+ "reference": "4c5cd619a89e6679fca80ff84036f68c554426a7",
+ "shasum": "06b7f2387c140b9b0f66d86fcfb2947ccebd1886"
+ },
+ "require": {
+ "cubist/net": "dev-master",
+ "ext-dom": "*",
+ "ext-iconv": "*",
+ "ext-json": "*",
+ "ext-libxml": "*",
+ "ext-mbstring": "*",
+ "ext-simplexml": "*",
+ "laravel/framework": "~5.8|^6.0|^7.0|^8.0",
+ "php": ">=7.0.0"
+ },
+ "type": "library",
+ "autoload": {
+ "psr-4": {
+ "Cubist\\Util\\": "src"
+ }
+ },
+ "license": [
+ "proprietary"
+ ],
+ "authors": [
+ {
+ "name": "Vincent Vanwaelscappel",
+ "email": "vincent@cubedesigners.com"
+ }
+ ],
+ "description": "Utilities class",
+ "time": "2021-04-20T13:58:22+00:00"
+ },
{
"name": "doctrine/inflector",
"version": "2.0.3",
},
{
"name": "laravel/framework",
- "version": "v8.37.0",
+ "version": "v8.38.0",
"source": {
"type": "git",
"url": "https://github.com/laravel/framework.git",
- "reference": "cf4082973abc796ec285190f0603380021f6d26f"
+ "reference": "26a73532c54d2c090692bf2e3e64e449669053ba"
},
"dist": {
"type": "zip",
- "url": "https://api.github.com/repos/laravel/framework/zipball/cf4082973abc796ec285190f0603380021f6d26f",
- "reference": "cf4082973abc796ec285190f0603380021f6d26f",
+ "url": "https://api.github.com/repos/laravel/framework/zipball/26a73532c54d2c090692bf2e3e64e449669053ba",
+ "reference": "26a73532c54d2c090692bf2e3e64e449669053ba",
"shasum": ""
},
"require": {
"issues": "https://github.com/laravel/framework/issues",
"source": "https://github.com/laravel/framework"
},
- "time": "2021-04-13T13:49:49+00:00"
+ "time": "2021-04-20T13:50:21+00:00"
},
{
"name": "laravel/tinker",
},
{
"name": "symfony/deprecation-contracts",
- "version": "v2.2.0",
+ "version": "v2.4.0",
"source": {
"type": "git",
"url": "https://github.com/symfony/deprecation-contracts.git",
- "reference": "5fa56b4074d1ae755beb55617ddafe6f5d78f665"
+ "reference": "5f38c8804a9e97d23e0c8d63341088cd8a22d627"
},
"dist": {
"type": "zip",
- "url": "https://api.github.com/repos/symfony/deprecation-contracts/zipball/5fa56b4074d1ae755beb55617ddafe6f5d78f665",
- "reference": "5fa56b4074d1ae755beb55617ddafe6f5d78f665",
+ "url": "https://api.github.com/repos/symfony/deprecation-contracts/zipball/5f38c8804a9e97d23e0c8d63341088cd8a22d627",
+ "reference": "5f38c8804a9e97d23e0c8d63341088cd8a22d627",
"shasum": ""
},
"require": {
"type": "library",
"extra": {
"branch-alias": {
- "dev-master": "2.2-dev"
+ "dev-main": "2.4-dev"
},
"thanks": {
"name": "symfony/contracts",
"description": "A generic function and convention to trigger deprecation notices",
"homepage": "https://symfony.com",
"support": {
- "source": "https://github.com/symfony/deprecation-contracts/tree/master"
+ "source": "https://github.com/symfony/deprecation-contracts/tree/v2.4.0"
},
"funding": [
{
"type": "tidelift"
}
],
- "time": "2020-09-07T11:33:47+00:00"
+ "time": "2021-03-23T23:28:01+00:00"
},
{
"name": "symfony/error-handler",
},
{
"name": "symfony/event-dispatcher-contracts",
- "version": "v2.2.0",
+ "version": "v2.4.0",
"source": {
"type": "git",
"url": "https://github.com/symfony/event-dispatcher-contracts.git",
- "reference": "0ba7d54483095a198fa51781bc608d17e84dffa2"
+ "reference": "69fee1ad2332a7cbab3aca13591953da9cdb7a11"
},
"dist": {
"type": "zip",
- "url": "https://api.github.com/repos/symfony/event-dispatcher-contracts/zipball/0ba7d54483095a198fa51781bc608d17e84dffa2",
- "reference": "0ba7d54483095a198fa51781bc608d17e84dffa2",
+ "url": "https://api.github.com/repos/symfony/event-dispatcher-contracts/zipball/69fee1ad2332a7cbab3aca13591953da9cdb7a11",
+ "reference": "69fee1ad2332a7cbab3aca13591953da9cdb7a11",
"shasum": ""
},
"require": {
"type": "library",
"extra": {
"branch-alias": {
- "dev-master": "2.2-dev"
+ "dev-main": "2.4-dev"
},
"thanks": {
"name": "symfony/contracts",
"standards"
],
"support": {
- "source": "https://github.com/symfony/event-dispatcher-contracts/tree/v2.2.0"
+ "source": "https://github.com/symfony/event-dispatcher-contracts/tree/v2.4.0"
},
"funding": [
{
"type": "tidelift"
}
],
- "time": "2020-09-07T11:33:47+00:00"
+ "time": "2021-03-23T23:28:01+00:00"
},
{
"name": "symfony/finder",
},
{
"name": "symfony/http-client-contracts",
- "version": "v2.3.1",
+ "version": "v2.4.0",
"source": {
"type": "git",
"url": "https://github.com/symfony/http-client-contracts.git",
- "reference": "41db680a15018f9c1d4b23516059633ce280ca33"
+ "reference": "7e82f6084d7cae521a75ef2cb5c9457bbda785f4"
},
"dist": {
"type": "zip",
- "url": "https://api.github.com/repos/symfony/http-client-contracts/zipball/41db680a15018f9c1d4b23516059633ce280ca33",
- "reference": "41db680a15018f9c1d4b23516059633ce280ca33",
+ "url": "https://api.github.com/repos/symfony/http-client-contracts/zipball/7e82f6084d7cae521a75ef2cb5c9457bbda785f4",
+ "reference": "7e82f6084d7cae521a75ef2cb5c9457bbda785f4",
"shasum": ""
},
"require": {
},
"type": "library",
"extra": {
- "branch-version": "2.3",
"branch-alias": {
- "dev-main": "2.3-dev"
+ "dev-main": "2.4-dev"
},
"thanks": {
"name": "symfony/contracts",
"standards"
],
"support": {
- "source": "https://github.com/symfony/http-client-contracts/tree/v2.3.1"
+ "source": "https://github.com/symfony/http-client-contracts/tree/v2.4.0"
},
"funding": [
{
"type": "tidelift"
}
],
- "time": "2020-10-14T17:08:19+00:00"
+ "time": "2021-04-11T23:07:08+00:00"
},
{
"name": "symfony/http-foundation",
},
{
"name": "symfony/service-contracts",
- "version": "v2.2.0",
+ "version": "v2.4.0",
"source": {
"type": "git",
"url": "https://github.com/symfony/service-contracts.git",
- "reference": "d15da7ba4957ffb8f1747218be9e1a121fd298a1"
+ "reference": "f040a30e04b57fbcc9c6cbcf4dbaa96bd318b9bb"
},
"dist": {
"type": "zip",
- "url": "https://api.github.com/repos/symfony/service-contracts/zipball/d15da7ba4957ffb8f1747218be9e1a121fd298a1",
- "reference": "d15da7ba4957ffb8f1747218be9e1a121fd298a1",
+ "url": "https://api.github.com/repos/symfony/service-contracts/zipball/f040a30e04b57fbcc9c6cbcf4dbaa96bd318b9bb",
+ "reference": "f040a30e04b57fbcc9c6cbcf4dbaa96bd318b9bb",
"shasum": ""
},
"require": {
"php": ">=7.2.5",
- "psr/container": "^1.0"
+ "psr/container": "^1.1"
},
"suggest": {
"symfony/service-implementation": ""
"type": "library",
"extra": {
"branch-alias": {
- "dev-master": "2.2-dev"
+ "dev-main": "2.4-dev"
},
"thanks": {
"name": "symfony/contracts",
"standards"
],
"support": {
- "source": "https://github.com/symfony/service-contracts/tree/master"
+ "source": "https://github.com/symfony/service-contracts/tree/v2.4.0"
},
"funding": [
{
"type": "tidelift"
}
],
- "time": "2020-09-07T11:33:47+00:00"
+ "time": "2021-04-01T10:43:52+00:00"
},
{
"name": "symfony/string",
},
{
"name": "symfony/translation-contracts",
- "version": "v2.3.0",
+ "version": "v2.4.0",
"source": {
"type": "git",
"url": "https://github.com/symfony/translation-contracts.git",
- "reference": "e2eaa60b558f26a4b0354e1bbb25636efaaad105"
+ "reference": "95c812666f3e91db75385749fe219c5e494c7f95"
},
"dist": {
"type": "zip",
- "url": "https://api.github.com/repos/symfony/translation-contracts/zipball/e2eaa60b558f26a4b0354e1bbb25636efaaad105",
- "reference": "e2eaa60b558f26a4b0354e1bbb25636efaaad105",
+ "url": "https://api.github.com/repos/symfony/translation-contracts/zipball/95c812666f3e91db75385749fe219c5e494c7f95",
+ "reference": "95c812666f3e91db75385749fe219c5e494c7f95",
"shasum": ""
},
"require": {
"type": "library",
"extra": {
"branch-alias": {
- "dev-master": "2.3-dev"
+ "dev-main": "2.4-dev"
},
"thanks": {
"name": "symfony/contracts",
"standards"
],
"support": {
- "source": "https://github.com/symfony/translation-contracts/tree/v2.3.0"
+ "source": "https://github.com/symfony/translation-contracts/tree/v2.4.0"
},
"funding": [
{
"type": "tidelift"
}
],
- "time": "2020-09-28T13:05:58+00:00"
+ "time": "2021-03-23T23:28:01+00:00"
},
{
"name": "symfony/var-dumper",
],
"aliases": [],
"minimum-stability": "dev",
- "stability-flags": [],
+ "stability-flags": {
+ "cubist/util": 20
+ },
"prefer-stable": true,
"prefer-lowest": false,
"platform": {
- "php": "^7.3|^8.0"
+ "php": "^7.3|^8.0",
+ "ext-json": "*"
},
"platform-dev": [],
"plugin-api-version": "2.0.0"