cli-barcode PHP
Ви не можете вибрати більше 25 тем Теми мають розпочинатися з літери або цифри, можуть містити дефіси (-) і не повинні перевищувати 35 символів.
 
 
 

389 рядки
11 KiB

  1. #!/usr/bin/env php
  2. <?php
  3. ##########################################################################
  4. # Gustavo Arnosti Neves - 2016 Jul 11
  5. # guneves < a t > gmail < d o t > com
  6. #
  7. # PHP cli-barcode-generator
  8. #
  9. # Most of the work here is for option / argument parsing.
  10. # Picqer's barcode framework makes it east on the bar coding generation.
  11. # While ulrichsg's getopt-php helps with the cli part.
  12. #
  13. ##########################################################################
  14. require_once 'vendor/autoload.php';
  15. define("_BC_VERSION", "1.0.6");
  16. # default padding for cli messages
  17. define("_BC_PADDING", 30);
  18. define("_BC_HELP_NEWLINE", "\n ");
  19. $verbose = false;
  20. $quiet = false;
  21. $encoding = null;
  22. $format = null;
  23. $bc_string = null;
  24. $bc_file = null;
  25. $width = 2;
  26. $height = 30;
  27. $color = '#000000';
  28. #$_defPermission = $false; # to be implemented
  29. #$_defGroup = $false; # to be implemented
  30. $encodings_list = array(
  31. 'CODE_39',
  32. 'CODE_39_CHECKSUM',
  33. 'CODE_39E',
  34. 'CODE_39E_CHECKSUM',
  35. 'CODE_93',
  36. 'STANDARD_2_5',
  37. 'STANDARD_2_5_CHECKSUM',
  38. 'INTERLEAVED_2_5',
  39. 'INTERLEAVED_2_5_CHECKSUM',
  40. 'CODE_128',
  41. 'CODE_128_A',
  42. 'CODE_128_B',
  43. 'CODE_128_C',
  44. 'EAN_2',
  45. 'EAN_5',
  46. 'EAN_8',
  47. 'EAN_13',
  48. 'UPC_A',
  49. 'UPC_E',
  50. 'MSI',
  51. 'MSI_CHECKSUM',
  52. 'POSTNET',
  53. 'PLANET',
  54. 'RMS4CC',
  55. 'KIX',
  56. 'IMB',
  57. 'CODABAR',
  58. 'CODE_11',
  59. 'PHARMA_CODE',
  60. 'PHARMA_CODE_TWO_TRACKS'
  61. );
  62. sort($encodings_list);
  63. $formats_list = array(
  64. 'SVG',
  65. 'PNG',
  66. 'JPG',
  67. 'HTML'
  68. );
  69. sort($formats_list);
  70. # Converts Hex Color to array(r, g, b, [a])
  71. function hexToRgb($hex) {
  72. $hex = str_replace('#', '', $hex);
  73. $length = strlen($hex);
  74. $rgb[] = hexdec($length == 6 ? substr($hex, 0, 2) : ($length == 3 ? str_repeat(substr($hex, 0, 1), 2) : 0));
  75. $rgb[] = hexdec($length == 6 ? substr($hex, 2, 2) : ($length == 3 ? str_repeat(substr($hex, 1, 1), 2) : 0));
  76. $rgb[] = hexdec($length == 6 ? substr($hex, 4, 2) : ($length == 3 ? str_repeat(substr($hex, 2, 1), 2) : 0));
  77. return $rgb;
  78. }
  79. /////////////////// PRINT HELP
  80. function getVersionString($suffix='') {
  81. return "PHP-CLI Barcode v"._BC_VERSION.$suffix;
  82. }
  83. function printVersion($suffix='') {
  84. echo getVersionString($suffix)."\n";
  85. }
  86. // prints help information
  87. function print_help($getopt) {
  88. global $encodings_list;
  89. global $formats_list;
  90. echo $getopt->getHelpText(_BC_PADDING);
  91. echo "\nRequired Options and Parameters:\n";
  92. echo " -e <encoding>\n";
  93. echo " -f <output format>\n";
  94. echo " <input string>\n";
  95. echo " <output file>\n";
  96. echo "\nOutput Formats:\n";
  97. foreach($formats_list as $for) {
  98. echo " $for\n";
  99. }
  100. echo "\nEncodings:\n";
  101. foreach($encodings_list as $enc) {
  102. echo " $enc\n";
  103. }
  104. echo "\nExamples:\n";
  105. echo " barcode -f HTML -e CODE_39 \"1234567890\" \"/tmp/1234567890.html\"\n";
  106. echo " barcode -e CODE_128 -f PNG -c \"#888\" -w 3 -h 50 \"AGREATBAR\" \"/tmp/AGREATBAR.png\"\n";
  107. echo " barcode \"1234567890\" \"/tmp/mybar.svg\" --encoding EAN_13 --format SVG\n";
  108. }
  109. /////////////////// CREATE SH SCRIPT
  110. // creates a shell script named barcode that will run this script
  111. // from anywhere on the system. Assumes barcode.php is running
  112. // on its final installation location
  113. function create_bash_script() {
  114. $error = true;
  115. $bc_path = __FILE__;
  116. $bash_path = dirname($bc_path) . DIRECTORY_SEPARATOR . "barcode";
  117. $bash_script = <<<EOF
  118. #!/usr/bin/env sh
  119. ##################################################
  120. # Gustavo Arnosti Neves - 2016 Jul 11
  121. # Simple bash script for global barcode executable
  122. # PHP cli-barcode-generator
  123. #
  124. # Please run "./barcode.php --create-bash" to update this script
  125. # You can then use sudo make install to copy it to /usr/local/bin
  126. #
  127. # This won't work on windows
  128. #
  129. BARCODE_LOCATION="$bc_path" # enter full path here
  130. /usr/bin/env php "\$BARCODE_LOCATION" "\$@"
  131. EOF;
  132. if (file_exists($bash_path)) {
  133. unlink($bash_path) or die("Could not remove old barcode script, are you running from it?");
  134. }
  135. $error = file_put_contents($bash_path, $bash_script) === true ? false : true;
  136. $error = chmod($bash_path, 0755) === true ? false : true;
  137. if ($error) {
  138. echo "\nAn error was detected during the process.\n";
  139. echo "Please check for permissions and try again.\n\n";
  140. exit(2);
  141. }
  142. echo "\nThe file \"$bash_path\" was successfully created.\n";
  143. echo "You may perform a system install to /usr/local/bin by issuing\n";
  144. echo "the command \"sudo make install\"\n\n";
  145. exit(0);
  146. }
  147. /////////////////// GETOPT STARTS
  148. use Ulrichsg\Getopt\Getopt;
  149. use Ulrichsg\Getopt\Option;
  150. use Ulrichsg\Getopt\Argument;
  151. // check if encoding callback
  152. function isEncoding($enc=null) {
  153. global $encodings_list;
  154. return in_array(strtoupper($enc), $encodings_list);
  155. }
  156. // check if format callback
  157. function isFormat($format=null) {
  158. global $formats_list;
  159. return in_array(strtoupper($format), $formats_list);
  160. }
  161. // check if empty callback
  162. function not_empty($str) {
  163. return (!empty($str));
  164. }
  165. // check if empty callback
  166. function isHexColor($str) {
  167. $str = str_replace('#', '', $str);
  168. if (! ctype_alnum($str) || (strlen($str) !== 6 && strlen($str) !== 3)) return false;
  169. return true;
  170. }
  171. function checkQuietExit($exitStat=0) {
  172. global $quiet;
  173. if ($quiet) ob_end_clean();
  174. exit($exitStat);
  175. }
  176. // define and configure options
  177. $getopt = new Getopt(array(
  178. (new Option('e', 'encoding', Getopt::REQUIRED_ARGUMENT))
  179. ->setDescription('Barcode encoding type selection, listed below')
  180. ->setArgument(new Argument(null, 'isEncoding', 'bar-type')),
  181. (new Option('f', 'format', Getopt::REQUIRED_ARGUMENT))
  182. ->setDescription('Output format for the barcode, listed below')
  183. ->setArgument(new Argument(null, 'isFormat', 'file-type')),
  184. (new Option('w', 'width', Getopt::REQUIRED_ARGUMENT))
  185. ->setDescription('Width factor for bars to make wider, defaults to 2')
  186. ->setArgument(new Argument(2, 'is_numeric', 'points')),
  187. (new Option('h', 'height', Getopt::REQUIRED_ARGUMENT))
  188. ->setDescription('Total height of the barcode, defaults to 30')
  189. ->setArgument(new Argument(30, 'is_numeric', 'points')),
  190. (new Option('c', 'color', Getopt::REQUIRED_ARGUMENT))
  191. ->setDescription('Hex code of the foreground color, defaults to black'._BC_HELP_NEWLINE."Eg. -c 54863b, or -c '#000'")
  192. ->setArgument(new Argument('#000000', 'isHexColor', 'hex-color')),
  193. (new Option('v', 'verbose'))
  194. ->setDescription('Prints verbose information to screen'._BC_HELP_NEWLINE."Use twice for timestamp")
  195. ->setDefaultValue(false),
  196. (new Option('q', 'quiet'))
  197. ->setDescription('Supress all messages, even errors')
  198. ->setDefaultValue(false),
  199. (new Option(null, 'help'))
  200. ->setDescription('Help Information, including encodings and formats'),
  201. (new Option(null, 'version'))
  202. ->setDescription('Display version information and exits'),
  203. (new Option(null, 'create-bash'))
  204. ->setDescription('Creates a shell script named \'barcode\' that can call this script')
  205. ));
  206. $getopt->setBanner("Usage: barcode -e <encoding> -f <output_format> [options] <barcode string> <output file>\n");
  207. try {
  208. $getopt->parse();
  209. if ($getopt['version']) {
  210. printVersion();
  211. exit(0);
  212. }
  213. if ($getopt['help']) {
  214. print_help($getopt);
  215. exit(0);
  216. }
  217. if ($getopt['create-bash']) {
  218. create_bash_script();
  219. exit(1);
  220. }
  221. $verbose = $getopt['verbose'];
  222. $quiet = $getopt['quiet'];
  223. $encoding = $getopt['encoding'];
  224. $format = $getopt['format'];
  225. $width = $getopt['width'];
  226. $height = $getopt['height'];
  227. $color = '#'.str_replace('#', '', $getopt['color']);
  228. $bc_string = $getopt->getOperand(0);
  229. $bc_file = $getopt->getOperand(1);
  230. } catch (UnexpectedValueException $e) {
  231. echo "Error: ".$e->getMessage()."\n";
  232. echo $getopt->getHelpText(_BC_PADDING);
  233. exit(1);
  234. }
  235. // check if we can proceed
  236. if (empty($encoding) || empty($format) || empty($bc_string) || empty($bc_file)) {
  237. echo "Error: Invalid parameters or options.\n";
  238. echo $getopt->getHelpText(_BC_PADDING);
  239. exit(1);
  240. }
  241. // check output directory
  242. $tgtDir = dirname($bc_file);
  243. if (! is_dir($tgtDir)) {
  244. echo "Error: Could not locate target directory!\nTarget Dir: $tgtDir\n";
  245. exit(1);
  246. }
  247. // Match case
  248. $encoding = strtoupper($encoding);
  249. $format = strtoupper($format);
  250. /////////////////// QUIET EXECUTION STARTS
  251. // From here on use checkQuietExit() to Exit
  252. if ($quiet) {
  253. ob_start();
  254. }
  255. /////////////////// GETOPT ENDS
  256. /////////////////// PRINT VERBOSE INFO
  257. vPrint(getVersionString(" - Verbose Execution"));
  258. vPrint(array("Output File", "$bc_file"));
  259. vPrint(array("Barcode String", "$bc_string"));
  260. vPrint(array("Barcode Encoding", "$encoding"));
  261. vPrint(array("Output Format", "$format"));
  262. vPrint(array("Width Factor", "$width"));
  263. vPrint(array("Height of Barcode", "$height"));
  264. vPrint(array("Hex Color", "$color"));
  265. function vPrint($input) {
  266. global $verbose;
  267. if ($verbose) {
  268. if ($verbose > 1) echo date(DATE_ATOM) . " | ";
  269. if (is_array($input) && count($input) > 1) {
  270. printf("%-17s : %-30s\n", $input[0], $input[1]);
  271. } else if (is_string($input)) {
  272. echo "$input\n";
  273. }
  274. }
  275. }
  276. /////////////////// CREATE BARCODE STARTS
  277. // get actual barcode type string
  278. $bc_type = constant('Picqer\Barcode\BarcodeGenerator::TYPE_'.$encoding);
  279. // add trailling zero if odd digits on Code128C
  280. $bc_string = strlen($bc_string) % 2 == 0 && $encoding === 'CODE_128_C'?
  281. $bc_string : '0'.$bc_string;
  282. // create appropriate generator
  283. $generator = null;
  284. if ($format === 'SVG') {
  285. $generator = new Picqer\Barcode\BarcodeGeneratorSVG();
  286. } else if ($format === 'PNG') {
  287. $color = hexToRgb($color);
  288. $generator = new Picqer\Barcode\BarcodeGeneratorPNG();
  289. } else if ($format === 'JPG') {
  290. $color = hexToRgb($color);
  291. $generator = new Picqer\Barcode\BarcodeGeneratorJPG();
  292. } else if ($format === 'HTML') {
  293. $generator = new Picqer\Barcode\BarcodeGeneratorHTML();
  294. } else {
  295. echo "Error: Invalid taget format: $format\n";
  296. checkQuietExit(1);
  297. }
  298. // generate de barcode
  299. try {
  300. $bc_data = $generator->getBarcode($bc_string, $bc_type, $width, $height, $color);
  301. } catch (Exception $e) {
  302. echo "Error: ".$e->getMessage()."\n";
  303. checkQuietExit(1);
  304. }
  305. // save to file
  306. if (@file_put_contents($bc_file, $bc_data) === false) {
  307. echo "Error: could not save file $bc_file!\n";
  308. checkQuietExit(1);
  309. }
  310. // set permissions and group
  311. #chmod($bc_file, $_defPermission);
  312. #chgrp($bc_file, $_defGroup);
  313. /////////////////// CREATE BARCODE ENDS
  314. /////////////////// PRINT VERBOSE INFO ENDS
  315. vprint(array("Final Status", "Success"));
  316. checkQuietExit(0);
  317. ?>