Completed
Push — master ( b55b66...72a785 )
by Basil
03:28
created

Boot::setIsCli()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 4

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
dl 0
loc 4
rs 10
c 0
b 0
f 0
cc 1
nc 1
nop 1
1
<?php
2
3
namespace luya\base;
4
5
use Yii;
6
use ReflectionClass;
7
use luya\Exception;
8
use luya\web\Application as WebApplication;
9
use luya\console\Application as ConsoleApplication;
10
use luya\helpers\ArrayHelper;
11
12
/**
13
 * LUYA Boot wrapper.
14
 *
15
 * Run the Luya/Yii Application based on the current enviroment which is determined trough get_sapi_name(). To run an application
16
 * a config file with custom Luya/Yii configuration must be provided via `$configFile` property. By default luya will try to find
17
 * the default config `../configs/env.php`.
18
 *
19
 * @property boolean $isCli Whether current request is runing in cli env or not.
20
 * @property string $baseYiiFile Returns the path to the yii base file.
21
 * 
22
 * @author Basil Suter <[email protected]>
23
 * @since 1.0.0
24
 */
25
abstract class Boot
26
{
27
    /**
28
     * @var string The current LUYA version (see: https://github.com/luyadev/luya/blob/master/core/CHANGELOG.md)
29
     */
30
    const VERSION = '1.0.12';
31
    
32
    /**
33
     * @var string The path to the config file, which returns an array containing you configuration.
34
     */
35
    public $configFile = '../configs/env.php';
36
37
    /**
38
     * @var \luya\web\Application|\luya\console\Application The application object.
39
     */
40
    public $app;
41
42
    /**
43
     * @var bool When enabled the boot process will not return/echo something, but the variabled will contain the Application object.
44
     */
45
    public $mockOnly = false;
46
47
    /**
48
     * @var string Path to the Yii.php file.
49
     */
50
    private $_baseYiiFile;
51
52
    /**
53
     * Setter method for the base Yii file.
54
     *
55
     * Example path to the yii base file:
56
     *
57
     * ```php
58
     * $boot->setYiiPath(__DIR__ . '/../vendor/yiisoft/yii2/Yii.php');
59
     * ```
60
     *
61
     * @param string $baseYiiFile The path to the Yii.php file.
62
     */
63
    public function setBaseYiiFile($baseYiiFile)
64
    {
65
        $this->_baseYiiFile = $baseYiiFile;
66
    }
67
    
68
    /**
69
     * Getter method for Yii base file.
70
     * 
71
     * @return string
72
     */
73
    public function getBaseYiiFile()
74
    {
75
        return $this->_baseYiiFile;
76
    }
77
78
    /**
79
     * Whether current request is runing in cli env or not.
80
     * 
81
     * This is determined by php_sapi_name().
82
     * 
83
     * @return boolean
84
     * @deprecated Depreacted since 1.0.12 use getisCli() or $isCli instead.
85
     */
86
    public function isCli()
87
    {
88
        return $this->getIsCli();
89
    }
90
91
    private $_isCli;
92
93
    /**
94
     * Getter method whether current request is cli or not.
95
     * 
96
     * If not set via setIsCli() the value is determined trough php_sapi_name();
97
     * 
98
     * @return boolean Whether current request is console env or not.
99
     * @since 1.0.12
100
     */
101
    public function getIsCli()
102
    {
103
        if ($this->_isCli === null) {
104
            $this->_isCli = $this->getSapiName() === 'cli';
105
        }
106
107
        return $this->_isCli;
108
    }
109
110
    /**
111
     * Setter method for isCli.
112
     * 
113
     * @param boolean $isCli
114
     * @since 1.0.12
115
     */
116
    public function setIsCli($isCli)
117
    {
118
        $this->_isCli = $isCli;
119
    }
120
    
121
    /**
122
     * Returns the current sapi name in lower case.
123
     *
124
     * @return string e.g. cli or web
125
     */
126
    public function getSapiName()
127
    {
128
        return strtolower(php_sapi_name());
129
    }
130
131
    private $_configArray;
132
    
133
    /**
134
     * This method allows you to directly inject a configuration array instead of using the config file
135
     * method.
136
     *
137
     * This method is commonly used when running php unit tests which do not require an additional file.
138
     *
139
     * ```php
140
     * $app = new Boot();
141
     * $app->setConfigArray([
142
     *     // ...
143
     * ]);
144
     * ```
145
     *
146
     * @param array $config The configuration array for the application.
147
     */
148
    public function setConfigArray(array $config)
149
    {
150
        $this->_configArray = $config;
151
    }
152
    
153
    /**
154
     * The prependConfigArray will be merged into the config, this way you can prepand config values for a custom Boot class.
155
     *
156
     * > When using prependConfig inside a custom boot class, the custom boot class will not used in the vendor bin file `./vendor/bin/luya`,
157
     * > so make sure to generate your own bin file.
158
     *
159
     * @return array
160
     */
161
    public function prependConfigArray()
162
    {
163
        return [];
164
    }
165
    
166
    /**
167
     * Get the config array from the configFile path with the predefined values.
168
     *
169
     * @throws \luya\Exception Throws exception if the config file does not exists.
170
     * @return array The array which will be injected into the Application Constructor.
171
     */
172
    public function getConfigArray()
173
    {
174
        if ($this->_configArray === null) {
175
            if (!file_exists($this->configFile)) {
176
                if (!$this->isCli) {
177
                    throw new Exception("Unable to load the config file '".$this->configFile."'.");
178
                }
179
                
180
                $config = ['id' => 'consoleapp', 'basePath' => dirname(__DIR__)];
181
            } else {
182
                $config = require $this->configFile;
183
            }
184
    
185
            if (!is_array($config)) {
186
                throw new Exception("config file '".$this->configFile."' found but no array returning.");
187
            }
188
            
189
            // preset the values from the defaultConfigArray
190
            if (!empty($this->prependConfigArray())) {
191
                $config = ArrayHelper::merge($config, $this->prependConfigArray());
192
            }
193
         
194
            $this->_configArray = $config;
195
        }
196
197
        return $this->_configArray;
198
    }
199
200
    /**
201
     * Run the application based on the Sapi Name.
202
     *
203
     * @return \luya\web\Application|\luya\console\Application Application objected based on the sapi name.
204
     */
205
    public function run()
206
    {
207
        if ($this->isCli) {
208
            return $this->applicationConsole();
209
        }
210
211
        return $this->applicationWeb();
212
    }
213
214
    /**
215
     * Run Cli-Application based on the provided config file.
216
     *
217
     * @return string|integer
218
     */
219
    public function applicationConsole()
220
    {
221
        $this->setIsCli(true);
222
        $config = $this->getConfigArray();
223
        $config['defaultRoute'] = 'help';
224
        if (isset($config['components'])) {
225
            if (isset($config['components']['composition'])) {
226
                unset($config['components']['composition']);
227
            }
228
        }
229
        
230
        $baseUrl = null;
231
        if (isset($config['consoleBaseUrl'])) {
232
            $baseUrl = $config['consoleBaseUrl'];
233
        } elseif (isset($config['consoleHostInfo'])) {
234
            $baseUrl = '/';
235
        }
236
        
237
        $this->includeYii();
238
        $mergedConfig = ArrayHelper::merge($config, [
239
            'bootstrap' => ['luya\console\Bootstrap'],
240
            'components' => [
241
                'urlManager' => [
242
                    'class' => 'yii\web\UrlManager',
243
                    'enablePrettyUrl' => true,
244
                    'showScriptName' => false,
245
                    'baseUrl' => $baseUrl,
246
                    'hostInfo' => isset($config['consoleHostInfo']) ? $config['consoleHostInfo'] : null,
247
                ],
248
            ],
249
        ]);
250
        $this->app = new ConsoleApplication($mergedConfig);
251
        if (!$this->mockOnly) {
252
            exit($this->app->run());
253
        }
254
    }
255
256
    /**
257
     * Run Web-Application based on the provided config file.
258
     *
259
     * @return string Returns the Yii Application run() method if mock is disabled. Otherwise returns void
260
     */
261
    public function applicationWeb()
262
    {
263
        $config = $this->getConfigArray();
264
        $this->includeYii();
265
        $mergedConfig = ArrayHelper::merge($config, ['bootstrap' => ['luya\web\Bootstrap']]);
266
        $this->app = new WebApplication($mergedConfig);
267
        if (!$this->mockOnly) {
268
            return $this->app->run();
269
        }
270
    }
271
    
272
    /**
273
     * Returns the path to luya core files
274
     *
275
     * @return string The base path to the luya core folder.
276
     */
277
    public function getCoreBasePath()
278
    {
279
        $reflector = new ReflectionClass(get_class($this));
280
        return dirname($reflector->getFileName());
281
    }
282
    
283
    /**
284
     * Helper method to check whether the provided Yii Base file exists, if yes include and
285
     * return the file.
286
     *
287
     * @return bool Return value based on require_once command.
288
     * @throws Exception Throws Exception if the YiiBase file does not exists.
289
     */
290
    private function includeYii()
291
    {
292
        if (file_exists($this->_baseYiiFile)) {
293
            defined('LUYA_YII_VENDOR') ?: define('LUYA_YII_VENDOR', dirname($this->_baseYiiFile));
294
            
295
            $baseYiiFolder = LUYA_YII_VENDOR . DIRECTORY_SEPARATOR;
296
            $luyaYiiFile = $this->getCoreBasePath() . DIRECTORY_SEPARATOR .  'Yii.php';
297
            
298
            if (file_exists($luyaYiiFile)) {
299
                require_once($baseYiiFolder . 'BaseYii.php');
300
                require_once($luyaYiiFile);
301
            } else {
302
                require_once($baseYiiFolder . 'Yii.php');
303
            }
304
            
305
            Yii::setAlias('@luya', $this->getCoreBasePath());
306
            
307
            return true;
308
        }
309
310
        throw new Exception("YiiBase file does not exits '".$this->_baseYiiFile."'.");
311
    }
312
}
313