Symfony 4命令行开发:接收JSON产品数组并按规则排序返回
嘿,这需求很清晰!我帮你一步步实现这个Symfony 4命令,完美满足按价格升序、价格相同则按标题字母升序排序的要求。
实现步骤
1. 创建并编写Command类
首先用Symfony的命令生成器创建基础文件:
bin/console make:command SortProductsCommand
然后打开生成的src/Command/SortProductsCommand.php,替换成以下代码:
<?php namespace App\Command; use Symfony\Component\Console\Command\Command; use Symfony\Component\Console\Input\InputArgument; use Symfony\Component\Console\Input\InputInterface; use Symfony\Component\Console\Output\OutputInterface; use Symfony\Component\Console\Style\SymfonyStyle; class SortProductsCommand extends Command { protected static $defaultName = 'app:sort-products'; protected static $defaultDescription = '接收产品数组JSON,按价格升序、标题字母升序排序后返回'; protected function configure(): void { $this ->addArgument('products-json', InputArgument::REQUIRED, '包含产品数组的JSON字符串') ; } protected function execute(InputInterface $input, OutputInterface $output): int { $io = new SymfonyStyle($input, $output); $productsJson = $input->getArgument('products-json'); // 解码JSON参数并验证格式 $products = json_decode($productsJson, true); if (json_last_error() !== JSON_ERROR_NONE) { $io->error('无效的JSON格式:' . json_last_error_msg()); return Command::FAILURE; } if (!is_array($products)) { $io->error('传入的JSON必须是一个产品数组'); return Command::FAILURE; } // 可选:验证每个产品都包含title和price字段 foreach ($products as $product) { if (!isset($product['title']) || !isset($product['price'])) { $io->error('所有产品必须包含title和price字段'); return Command::FAILURE; } } // 核心排序逻辑 usort($products, function ($a, $b) { // 先按价格升序比较 if ($a['price'] !== $b['price']) { return $a['price'] <=> $b['price']; } // 价格相同时,按标题字母升序(区分大小写,要忽略大小写用strcasecmp) return strcmp($a['title'], $b['title']); }); // 输出格式化后的JSON结果 $sortedJson = json_encode($products, JSON_PRETTY_PRINT | JSON_UNESCAPED_UNICODE); $io->writeln($sortedJson); return Command::SUCCESS; } }
2. 代码逻辑说明
- 命令配置:
configure()方法定义了必填的products-json参数,明确标注用途 - JSON验证:先解码参数,同时捕获格式错误;额外验证是否为数组,避免非法输入
- 排序逻辑:用
usort实现自定义排序:- 优先比较
price,用太空船运算符<=>直接实现升序逻辑 - 价格相同时,用
strcmp比较标题的字母顺序,严格遵循升序规则
- 优先比较
- 结果输出:用
JSON_PRETTY_PRINT让输出更易读,JSON_UNESCAPED_UNICODE保留特殊字符(比如示例里的"H&M"不会被转义)
3. 测试运行
用你提供的示例JSON(补全缺失部分),在命令行执行:
bin/console app:sort-products '[ {"title": "H&M T-Shirt White", "price": 10.99, "inventory": 10 }, {"title": "Magento Enterprise License", "price": 1999.99, "inventory": 9999 }, {"title": "iPad 4 Mini", "price": 500.01, "inventory": 5 }, {"title": "Nike Air Shoes", "price": 10.99, "inventory": 20 } ]'
会得到排序后的JSON结果:
[ { "title": "H&M T-Shirt White", "price": 10.99, "inventory": 10 }, { "title": "Nike Air Shoes", "price": 10.99, "inventory": 20 }, { "title": "iPad 4 Mini", "price": 500.01, "inventory": 5 }, { "title": "Magento Enterprise License", "price": 1999.99, "inventory": 9999 } ]
小提示
- 命令行传JSON时,一定要用单引号包裹整个字符串,避免bash解析双引号导致参数错乱
- 要是需要忽略标题的大小写排序,把
strcmp换成strcasecmp即可
内容的提问来源于stack exchange,提问作者Ekstermin Sir
相关产品推荐
相关产品推荐

