Completed
Push — epic/2.0.0 ( fdbf62...0828e2 )
by Steven
07:13 queued 04:31
created

NewCommand::execute()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 14
Code Lines 8

Duplication

Lines 0
Ratio 0 %

Importance

Changes 1
Bugs 0 Features 0
Metric Value
c 1
b 0
f 0
dl 0
loc 14
rs 9.4285
cc 1
eloc 8
nc 1
nop 2
1
<?php namespace Magestead\Command;
2
3
use Magestead\Exceptions\ExistingProjectException;
4
use Magestead\Helper\Options;
5
use Magestead\Installers\Project;
6
use Symfony\Component\Yaml\Parser;
7
use Symfony\Component\Yaml\Dumper;
8
use Symfony\Component\Console\Command\Command;
9
use Symfony\Component\Console\Helper\ProgressBar;
10
use Symfony\Component\Console\Input\InputArgument;
11
use Symfony\Component\Console\Input\InputInterface;
12
use Symfony\Component\Yaml\Exception\ParseException;
13
use Symfony\Component\Console\Output\OutputInterface;
14
15
/**
16
 * Class NewCommand
17
 * @package Magestead\Command
18
 */
19
class NewCommand extends Command
20
{
21
    protected $_basePath;
22
    protected $_projectPath;
23
    protected $_msConfig;
24
25
    protected function configure()
26
    {
27
        $this->_basePath    = dirname( __FILE__ ) . '/../../../';
28
        $this->_projectPath = getcwd();
29
30
        $this->setName("new");
31
        $this->setDescription("Initialise new Magestead project into current working directory");
32
        $this->addArgument('project', InputArgument::REQUIRED, 'Name your project directory');
33
    }
34
35
36
    /**
37
     * @param InputInterface $input
38
     * @param OutputInterface $output
39
     * @return \Magestead\Installers\Magento2Project|\Magestead\Installers\MagentoProject
40
     * @throws ExistingProjectException
41
     */
42
    protected function execute(InputInterface $input, OutputInterface $output)
43
    {
44
        $project = $this->setProject($input);
45
46
        $helper  = $this->getHelper('question');
47
        $options = new Options($helper, $input, $output, $project);
48
49
        $this->setupProject($output, $options);
50
51
        $output->writeln('<info>Spinning up your custom box</info>');
52
        new ProcessCommand('vagrant up', $this->_projectPath, $output);
53
54
        return Project::create($options->getAllOptions(), $this->_msConfig, $this->_projectPath, $output);
55
    }
56
57
    /**
58
     * @param $source
59
     * @param $target
60
     * @param OutputInterface $output
61
     */
62
    protected function copyConfigFiles($source, $target, OutputInterface $output)
63
    {
64
        try {
65
            $progress = new ProgressBar($output, 3720);
66
            $progress->start();
67
            foreach (
68
                $iterator = new \RecursiveIteratorIterator(
69
                    new \RecursiveDirectoryIterator($source, \RecursiveDirectoryIterator::SKIP_DOTS),
70
                    \RecursiveIteratorIterator::SELF_FIRST) as $item
71
            ) {
72
                if ($item->isDir()) {
73
                    mkdir($target . DIRECTORY_SEPARATOR . $iterator->getSubPathName());
74
                } else {
75
                    copy($item, $target . DIRECTORY_SEPARATOR . $iterator->getSubPathName());
76
                }
77
                $progress->advance();
78
            }
79
            $progress->finish();
80
            echo "\n";
81
        } catch (\Exception $e) {
82
            $output->writeln('<error>There was an error while setting up the project structure</error>');
83
        }
84
    }
85
86
    /**
87
     * @param array $options
88
     * @param OutputInterface $output
89
     */
90
    protected function configureProject(array $options, OutputInterface $output)
91
    {
92
        $msConfig = $this->getConfigFile($output);
93
94
        $app = ($options['app'] == 'magento2') ? 'magento2' : 'magento';
95
        $hostname = 'magestead-' . $options['base_url'];
96
97
        $msConfig['vagrantfile']['vm']['box']                           = $options['box'];
98
        $msConfig['vagrantfile']['vm']['box_url']                       = $options['box'];
99
        $msConfig['vagrantfile']['vm']['hostname']                      = $hostname;
100
        $msConfig['vagrantfile']['vm']['memory']                        = $options['memory_limit'];
101
        $msConfig['vagrantfile']['vm']['network']['private_network']    = $options['ip_address'];
102
        $msConfig['magestead']['apps']['mba_12345']['type']             = $app;
103
        $msConfig['magestead']['apps']['mba_12345']['locale']           = $options['locale'];
104
        $msConfig['magestead']['apps']['mba_12345']['default_currency'] = $options['default_currency'];
105
        $msConfig['magestead']['apps']['mba_12345']['base_url']         = $options['base_url'];
106
        $msConfig['magestead']['os']                                    = $options['os'];
107
        $msConfig['magestead']['server']                                = $options['server'];
108
109
        $this->_msConfig = $msConfig;
110
111
        $this->saveConfigFile($msConfig, $output);
112
113
    }
114
115
    /**
116
     * @param OutputInterface $output
117
     * @return mixed
118
     */
119
    protected function getConfigFile(OutputInterface $output)
120
    {
121
        $yaml = new Parser();
122
        try {
123
            return $yaml->parse(file_get_contents($this->_projectPath . '/magestead.yaml'));
124
        } catch (ParseException $e) {
125
            $output->writeln('<error>Unable to parse the YAML string</error>');
126
            printf("Unable to parse the YAML string: %s", $e->getMessage());
127
        }
128
    }
129
130
    /**
131
     * @param array $config
132
     * @param OutputInterface $output
133
     */
134 View Code Duplication
    protected function saveConfigFile(array $config, OutputInterface $output)
0 ignored issues
show
Duplication introduced by
This method seems to be duplicated in your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
135
    {
136
        $dumper = new Dumper();
137
        $yaml   = $dumper->dump($config, 6);
138
139
        try {
140
            file_put_contents($this->_projectPath . '/magestead.yaml', $yaml);
141
        } catch (\Exception $e) {
142
            $output->writeln('<error>Unable to write to the YAML file</error>');
143
        }
144
    }
145
146
    /**
147
     * @param OutputInterface $output
148
     * @param $options
149
     */
150
    protected function setupProject(OutputInterface $output, $options)
151
    {
152
        $output->writeln('<info>Setting up project structure</info>');
153
        $provisionFolder = $this->_basePath . "provision";
154
        $this->copyConfigFiles($provisionFolder, $this->_projectPath, $output);
155
        $this->configureProject($options->getAllOptions(), $output);
156
    }
157
158
    /**
159
     * @param InputInterface $input
160
     * @return mixed
161
     * @throws ExistingProjectException
162
     */
163
    protected function setProject(InputInterface $input)
164
    {
165
        $project = $input->getArgument('project');
166
        $this->_projectPath = $this->_projectPath . '/' . $project;
167
168
169
        if (is_dir($this->_projectPath)) {
170
            throw new ExistingProjectException('Target project directory already exists');
171
        }
172
173
        mkdir($this->_projectPath, 0777, true);
174
        return $project;
175
    }
176
}
177