Issues (994)

src/MVC/themes.php (13 issues)

1
<?php
2
3
namespace MVC;
4
5
if (!function_exists('folder_session')) {
6
  include __DIR__ . '/loader.php';
7
}
8
9
use Filemanager\file;
10
use JSON\json;
11
12
class themes
13
{
14
  public $root_theme;
15
  public $theme;
16
  public $view;
17
  public $meta = [];
18
  public $title = '';
19
  public $config;
20
  public $config_folder;
21
  /**
22
   * Session instances.
23
   *
24
   * @var \Session\session
25
   */
26
  public $session = null;
27
28
  public function __construct()
29
  {
30
    /**
31
     * Load image cache if exists.
32
     */
33
    $imgproxy = isset($_REQUEST['image-proxy']) ? $_REQUEST['image-proxy'] : (isset($_REQUEST['img-source']) ? $_REQUEST['img-source'] : null);
34
    if ($imgproxy) {
35
      $url = urldecode(trim($imgproxy));
36
      if (helper::is_url($url)) {
37
        helper::cleanBuffer();
38
        exit(\img\cache::imageCache($url));
0 ignored issues
show
Using exit here is not recommended.

In general, usage of exit should be done with care and only when running in a scripting context like a CLI script.

Loading history...
39
      }
40
    }
41
42
    // @todo Setup default meta
43
    $this->meta = [
44
      'published' => date('m/j/y g:i A'),
45
      'modified' => date('m/j/y g:i A'),
46
      'thumbnail' => 'https://1.bp.blogspot.com/-rkXCUBbNXyw/XfY0hwoFu5I/AAAAAAAAAhw/BUyeKW5BtMoIJLlPUcPSdqGZBQRncXjDQCK4BGAYYCw/s600/PicsArt_09-09-12.12.25.jpg',
47
      'theme' => true,
48
      'title' => $_SERVER['REQUEST_URI'],
49
      'share' => false,
50
      'desc' => '',
51
      'content' => null,
52
      'robot' => 'noindex, nofollow',
53
      'obfuscate' => false,
54
      'cache' => false,
55
      'label' => 'default',
56
      'meta_config' => $this->config
57
    ];
58
59
    $this->root = realpath(__DIR__ . '/../../');
0 ignored issues
show
Bug Best Practice introduced by
The property root does not exist. Although not strictly required by PHP, it is generally a best practice to declare properties explicitly.
Loading history...
60
    $this->root_theme = realpath(__DIR__ . '/themes');
61
    $this->view = helper::platformSlashes($this->root . '/view');
62
    $this->config_folder = helper::platformSlashes(__DIR__ . '/config');
63
  }
64
65
  /**
66
   * Turn zone into maintenance mode (Maintenance page).
67
   *
68
   * @param string|array $zone if empty, will turn into maintenance mode in all zone
69
   *
70
   * @return \MVC\themes
71
   */
72
  public function shutdown($zone)
73
  {
74
    $current = get_zone();
75
76
    if (is_string($zone)) {
77
      if ($current == $zone) {
78
        maintenance();
79
      }
80
    } elseif (is_array($zone)) {
0 ignored issues
show
The condition is_array($zone) is always true.
Loading history...
81
      if (in_array($current, $zone)) {
82
        maintenance();
83
      }
84
    }
85
    if (empty($zone)) {
86
      maintenance();
87
    }
88
89
    return $this;
90
  }
91
92
  public function published($time)
93
  {
94
    $date = $this->date($time);
95
    $this->meta['published'] = $date;
96
97
    return $this;
98
  }
99
100
  public function modified($time)
101
  {
102
    $date = $this->date($time);
103
    $this->meta['modified'] = $date;
104
105
    return $this;
106
  }
107
108
  public function thumbnail($src)
109
  {
110
    $this->meta['thumbnail'] = $src;
111
  }
112
113
  public function date($time, $format = 'm/j/y g:i A')
114
  {
115
    if (!is_numeric($time)) {
116
      $time = strtotime($time);
117
    }
118
119
    return date($format, $time);
120
  }
121
122
  /**
123
   * Set Label Router.
124
   *
125
   * @return themes
126
   */
127
  public function label(string $label = 'default')
128
  {
129
    $this->meta['label'] = $label;
130
131
    return $this;
132
  }
133
134
  /**
135
   * Set theme default.
136
   *
137
   * @return $this
138
   */
139
  public function set(string $theme, bool $useTheme = true)
0 ignored issues
show
The parameter $useTheme is not used and could be removed. ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-unused  annotation

139
  public function set(string $theme, /** @scrutinizer ignore-unused */ bool $useTheme = true)

This check looks for parameters that have been defined for a function or method, but which are not used in the method body.

Loading history...
140
  {
141
    $this->theme = $theme;
142
    $this->root_theme = helper::platformSlashes($this->root_theme . '/' . $theme);
143
    return $this;
144
  }
145
146
  /**
147
   * ```php
148
   * setThemeByZones([ 'theme-name'=>['zone1', 'zone2'], 'another-theme'=>['zone3','zone4'], 'default-template'])
149
   * ```
150
   * Set theme by zone divider.
151
   * if not exists in zone divider, will using default template.
152
   *
153
   * @throws Exception
154
   *
155
   * @return $this
156
   */
157
  public function setThemeByZones(array $config, string $default)
158
  {
159
    $current = get_zone();
160
    $set = false;
161
    foreach ($config as $theme_name => $zones) {
162
      if (in_array($current, $zones)) {
163
        $this->set($theme_name);
164
        $set = true;
165
      }
166
    }
167
    if (!$set) {
168
      $this->set($default);
169
    }
170
171
    return $this;
172
  }
173
174
  public function view($file)
175
  {
176
    $this->view = helper::platformSlashes($this->root . '/' . $file);
177
    $this->view = str_replace(helper::platformSlashes($this->root), '', $this->view);
178
    $this->view = $this->root . $this->view;
179
180
    if (realpath($this->view)) {
181
      $this->view = realpath($this->view);
182
      $this->meta['content'] = $this->remove_root($this->view);
183
      $this->prepare_config();
184
185
      /**
186
       * begin form include.
187
       *
188
       * @todo Form includer
189
       */
190
      $form = preg_replace('/\.php$/s', '-f.php', $this->view);
191
      helper::include_asset($form);
192
      if (!$this->meta['theme'] && $this->NoThemeRequest()) {
193
        include $this->view;
194
195
        exit;
0 ignored issues
show
Using exit here is not recommended.

In general, usage of exit should be done with care and only when running in a scripting context like a CLI script.

Loading history...
196
      }
197
    }
198
199
    return $this;
200
  }
201
202
  /**
203
   * Remove root path
204
   */
205
  public function remove_root($path)
206
  {
207
    return str_replace($this->root, '', $path);
208
  }
209
210
  /**
211
   * Transform to linux separated file
212
   */
213
  public function fix_slash($path)
214
  {
215
    return preg_replace('/(\/|\\\\){2,100}/m', '/', $path);
216
  }
217
218
  public function prepare_config()
219
  {
220
    $viewNoRoot = str_replace($this->root, '', $this->view);
221
    $this->config = $this->config_folder . '/' . preg_replace('/\.php$/s', '', $viewNoRoot) . '.json';
222
    if ($config = helper::platformSlashes($this->config)) {
223
      $this->config = $config;
224
      if (!is_dir(dirname($config)) && !file_exists(dirname($config))) {
225
        mkdir(dirname($config), 0777, true);
226
      }
227
      if (!file_exists($config)) {
228
        file_put_contents($config, json_encode($this->meta, JSON_UNESCAPED_SLASHES | JSON_UNESCAPED_UNICODE | JSON_PRETTY_PRINT));
229
      } else {
230
        $this->meta = json_decode(file_get_contents($config), true);
231
        if (!isset($this->meta['robot'])) {
232
          $this->meta['robot'] = 'noindex, nofollow';
233
        }
234
        header('X-Robots-Tag: ' . trim($this->meta['robot']), true);
235
        // obfuscate javascript
236
        if (!isset($this->meta['obfuscate'])) {
237
          $this->meta['obfuscate'] = false;
238
        }
239
        // cache
240
        if (!isset($this->meta['cache'])) {
241
          $this->meta['cache'] = true;
242
        }
243
        $this->meta['content'] = $this->root . $this->meta['content'];
244
245
        if ($this->is_admin() && !helper::cors()) {
0 ignored issues
show
Bug Best Practice introduced by
The expression $this->is_admin() of type integer|null is loosely compared to true; this is ambiguous if the integer can be 0. You might want to explicitly use !== null instead.

In PHP, under loose comparison (like ==, or !=, or switch conditions), values of different types might be equal.

For integer values, zero is a special case, in particular the following results might be unexpected:

0   == false // true
0   == null  // true
123 == false // false
123 == null  // false

// It is often better to use strict comparison
0 === false // false
0 === null  // false
Loading history...
246
          //@todo set theme by parameter url
247
          if (isset($_GET['theme'])) {
248
            $this->meta['theme'] = 'true' == trim($_GET['theme']) ? true : false;
249
            file_put_contents($config, json_encode($this->meta, JSON_UNESCAPED_SLASHES | JSON_UNESCAPED_UNICODE | JSON_PRETTY_PRINT));
250
          }
251
          //@todo set theme by parameter url
252
          if (isset($_GET['obfuscate'])) {
253
            $this->meta['obfuscate'] = 'true' == trim($_GET['theme']) ? true : false;
254
            file_put_contents($config, json_encode($this->meta, JSON_UNESCAPED_SLASHES | JSON_UNESCAPED_UNICODE | JSON_PRETTY_PRINT));
255
          }
256
          //@todo reset config meta
257
          if (isset($_GET['reset-meta'])) {
258
            file::delete($config);
259
          }
260
        }
261
      }
262
    }
263
264
    return $this;
265
  }
266
267
  /**
268
   * Dump this variable.
269
   *
270
   * @param variadic ...$var
0 ignored issues
show
The type MVC\variadic was not found. Maybe you did not declare it correctly or list all dependencies?

The issue could also be caused by a filter entry in the build configuration. If the path has been excluded in your configuration, e.g. excluded_paths: ["lib/*"], you can move it to the dependency path list as follows:

filter:
    dependency_paths: ["lib/*"]

For further information see https://scrutinizer-ci.com/docs/tools/php/php-scrutinizer/#list-dependency-paths

Loading history...
271
   */
272
  public function dump(...$var)
273
  {
274
    if (ob_get_level()) {
275
      ob_end_clean();
276
      ob_start();
277
    }
278
    \JSON\json::headerJSON();
279
    exit(var_dump($var));
0 ignored issues
show
Using exit here is not recommended.

In general, usage of exit should be done with care and only when running in a scripting context like a CLI script.

Loading history...
Are you sure the usage of var_dump($var) is correct as it seems to always return null.

This check looks for function or method calls that always return null and whose return value is used.

class A
{
    function getObject()
    {
        return null;
    }

}

$a = new A();
if ($a->getObject()) {

The method getObject() can return nothing but null, so it makes no sense to use the return value.

The reason is most likely that a function or method is imcomplete or has been reduced for debug purposes.

Loading history...
Security Debugging Code introduced by
var_dump($var) looks like debug code. Are you sure you do not want to remove it?
Loading history...
280
  }
281
282
  public function is_admin()
283
  {
284
    if (isset($_SESSION['login']['role'])) {
285
      return preg_match(\User\user::get_admin_pattern(), $_SESSION['login']['role']);
286
    }
287
  }
288
289
  /*public function admin()
290
  {
291
    http_response_code(200);
292
    $this->root_theme = realpath(__DIR__ . '/themes');
293
    $view = $this->root_theme . '/admin/view.php';
294
    if ($form = realpath(preg_replace('/\.php$/s', '-f.php', $view))) {
295
      include $form;
296
    }
297
    $this->set('admin');
298
    $this->view($view);
299
    //var_dump($this);
300
    $this->render();
301
  }*/
302
303
  /**
304
   * Include passed variable.
305
   */
306
  public function render($variables = [], $print = true)
307
  {
308
    //exit('xxx');
309
    \MVC\helper::trycatch(function () use ($variables, $print) {
310
      $this->load_render($variables, $print);
311
    });
312
313
    return $this;
314
  }
315
316
  public function isJSONRequest()
317
  {
318
    $hasJSON = isset($_REQUEST['json']);
319
    if (!$hasJSON) {
320
      if (isset($_SERVER['HTTP_ACCEPT'])) {
321
        $hasJSON = preg_match('/^application\/json/m', $_SERVER['HTTP_ACCEPT']);
322
      }
323
    }
324
325
    return $hasJSON;
326
  }
327
328
  public function NoThemeRequest()
329
  {
330
    if (!isset($this->meta['theme']) || $this->meta['theme']) {
331
      return false;
332
    }
333
    $accept = isset($_SERVER['HTTP_ACCEPT']) ? $_SERVER['HTTP_ACCEPT'] : false;
334
    if (false !== $accept) {
335
      if (preg_match('/((application|text)\/(json|javascript))/m', $accept, $match)) {
336
        if (isset($match[0]) && !headers_sent()) {
337
          header('Content-Type: ' . $match[0]);
338
        }
339
340
        return true;
341
      }
342
    }
343
344
    return false;
345
  }
346
347
  public function load_render(array $variables, bool $print = true)
348
  {
349
    $this->meta['meta_config'] = fixpath($this->config);
350
    //exit(\JSON\json::json($this));
351
    if (file_exists($this->view)) {
352
      // Extract the variables to a local namespace
353
      extract($variables);
354
      extract($this->meta);
355
      $_SESSION['var'] = get_defined_vars();
356
      $content = $this->view;
357
358
      $theme = $this;
359
      //exit(\JSON\json::json($theme));
360
361
      // if not using theme
362
      if (!$this->meta['theme']) {
363
        include $content;
364
365
        return;
366
      } elseif ($this->meta['theme']) {
367
        // Include the template file
368
        $template_content = $this->root_theme . '/content.php';
369
        if (file_exists($template_content)) {
370
          include $template_content;
371
        } else {
372
          return json::json([
0 ignored issues
show
Are you sure the usage of JSON\json::json(array('e...ntent . ' not exists')) targeting JSON\json::json() seems to always return null.

This check looks for function or method calls that always return null and whose return value is used.

class A
{
    function getObject()
    {
        return null;
    }

}

$a = new A();
if ($a->getObject()) {

The method getObject() can return nothing but null, so it makes no sense to use the return value.

The reason is most likely that a function or method is imcomplete or has been reduced for debug purposes.

Loading history...
373
            'error' => true,
374
            'message' => $template_content . ' not exists',
375
          ]);
376
        }
377
      } else {
378
        exit('meta theme not defined');
0 ignored issues
show
Using exit here is not recommended.

In general, usage of exit should be done with care and only when running in a scripting context like a CLI script.

Loading history...
379
      }
380
381
      /*// End buffering and return its contents
382
      $output = ob_get_clean();*/
383
    } else {
384
      json::json([
385
        'error' => true,
386
        'message' => $this->view . ' not exists',
387
      ]);
388
      exit;
0 ignored issues
show
Using exit here is not recommended.

In general, usage of exit should be done with care and only when running in a scripting context like a CLI script.

Loading history...
389
    }
390
  }
391
392
  /**
393
   * Load admin tools
394
   */
395
  /*
396
  public function load_admin_tools()
397
  {
398
    if ($this->is_admin()) {
399
      $Config = normalize_path(realpath($this->config));
400
      include __DIR__ . '/themes/admin.php';
401
    }
402
  }
403
  */
404
}
405