Come on! Crazy for a PHP Modernization Framework (Preparation)

  Framework, laravel, php

clipboard.png

Preface

Starting from this chapter, we will continue to build wheels to complete a modern PHP framework similar to Laravel. Why is it modernization? Because he must have the following points

  • Comply with PSR-4 coding specification
  • Package Management Using Composer
  • Standard HTTP Request Method
  • Elegant Use of Design Patterns

At first, we don’t need to care about the performance problem. First, we need to consider what functions the framework needs to implement. This is very different from implementing business. Come on! Start my performance.

Early stage

To do anything, one must have a preparatory work.

  1. As required by PSR-4, our namespace must have an ancestor name, and here I call him the sacred “z_framework.”
  2. At least one GITHUB library is required to store this projecthttps://github.com/CrazyCodes …
  3. Creating a composer.json file for package management is usually simple, and phpunit comes in. Loading project names through psr-4

    {
     "name": "z framework",
     "require-dev": {
     "phpunit/phpunit": "^7.0"
     },
     "autoload": {
     "psr-4": {
     "Zero\\": "src/Zero",
     }
     },
     "autoload-dev": {
     "psr-4": {
     "Zero\\Tests\\": "tests/"
     }
     }
     }

Finally, we need to consider the structure of the directory and the functions we will complete in the first step, the core structure (here is not only the project structure. Is the core structure of the framework) for the time being

  • src

    • Zero

      • Config // parser that may hold some configuration files
      • Container // parser for container
      • Http // Some Tools for Request Processing
      • Routes // Some Functions of Route Processing
      • Bootstrap.php//This may be a startup script
      • Zero.php//may be the core entry file
  • Tests // test directory
  • .gitignore
  • composer.json
  • LICENSE
  • README.md

Routing

Do you remember the first step we took when we first used Laravel? Yes, to study routing, so we take routing as the first step in the framework. Before studying routing, we should know

http://www.domain.com/user/create

How is it implemented? php must request index.php or default.php by default. The above link actually hides index.php or default.php. This is an elegant link that Nginx and other service agents help us to achieve. The specific configuration is as follows, which is actually the same as that provided by Laravel authorities.

server {
 listen       80;
 server_name   www.zf.com ;
 root          /mnt/app/z_framework/server/public;
 index          index.php  index.html  index.htm ;
 
 location / {
 try_files $uri $uri/ /index.php?  $query_string;
 }
 
 location ~ \.php$ {
 fastcgi_pass   php71:9000;
 fastcgi_index   index.php ;
 fastcgi_param  SCRIPT_FILENAME  $document_root$fastcgi_script_name;
 include        fastcgi_params;
 }
 }

via

try_files $uri $uri/ /index.php?  $query_string;

To analyze the request, can be obtained from the above

http://www.domain.com/user/create
 =======
 http://www.domain.com/index.php?  user/create

Well, after we understand the mystery, we began to write the route, in src/routes/route.php.

namespace Zero\Routes;
 
 class Route
 {
 }

Realization

First, let’s create a simple interface file
src/Routes/RouteInterface.php

namespace Zero\Routes;
 
 interface RouteInterface
 {
 public function Get($url, $callFile);
 
 public function Post($url, $callFile);
 
 public function Put($url, $callFile);
 
 public function Delete($url, $callFile);
 }

Starting with a Get request

namespace Zero\Routes;
 
 class Route implements RouteInterface
 {
 public function Get($url, $callFile)
 {
 
 }
 }

Finally, Get code blocks are implemented.

If (parent:: isrequestmethod ("get")) {//interpret request method
 
 If (is_callable($callFile)) {// determines whether it is an anonymous function
 return $callFile();
 }
 
 If ($ breakupstring = parent:: breakupstring ($ callfile)) {//Get get get resolution.  Not only /user/create
 header('HTTP/1.1 404 Not Found');
 }
 
 try {
 //Get object $breakUpString[0] = user through reflection class
 $reflectionClass = new \ReflectionClass('App\\Controllers\\' . $breakUpString[0]);
 //Instantiate Objects
 $newInstance     = $reflectionClass->newInstance();
 //Get the specified method in the object, $breakUpString[1] = create
 call_user_func([
 $newInstance,
 $breakUpString[1],
 ], []);
 } catch (\ReflectionException $e) {
 header('HTTP/1.1 404 Not Found');
 }
 } else {
 header('HTTP/1.1 404 Not Found');
 }
 
 return "";

If you want to test the above code, you can use phpunit, or the silly way, which is easy to understand here.

clipboard.png

Create a directory, then create several directories according to Laravel’s directory format.

<?  php
 
 namespace App\Controllers;
 
 class UserController
 {
 public function create()
 {
 var_dump(0);
 }
 }

Finally, call the route in the public/index.php file.

require_once "../../vendor/autoload.php";
 
 Zero\Zero::Get("user", "UserController@create");

Here we have basically completed the function of routing, and the next chapter will improve the coding of routing.

Thank you

Thank you for seeing here. I hope this article can help you. The specific code ishttps://github.com/CrazyCodes …