php pop,GitHub - popphp/popphp: Pop PHP Framework Core Components

popphp

badge.svg

687474703a2f2f63632e706f707068702e6f72672f636f7665726167652e7068703f636f6d703d706f70706870

68747470733a2f2f6261646765732e6769747465722e696d2f4a6f696e253230436861742e737667

OVERVIEW

popphp is the main set of core components for the Pop PHP Framework.

It provides the main Application object that can be configured to manage

and interface with the underlying core components:

Router

Controller

Model

Module Manager

Event Manager

Service Locator

popphp is the main core component of the Pop PHP Framework.

INSTALL

Install popphp using Composer.

composer require popphp/popphp

DISCUSSION

There is an IRC channel for Pop PHP over at irc://freenode/popphp.

BASIC USAGE

The Application Object

Here's a simple example of wiring a web application object with a

configuration file that defines some basic routes:

application.php

return [

'routes' => [

'/' => [

'controller' => 'MyApp\Controller\IndexController',

'action' => 'index'

],

'/users[/]' => [

'controller' => 'MyApp\Controller\IndexController',

'action' => 'users'

],

'/edit/:id' => [

'controller' => 'MyApp\Controller\IndexController',

'action' => 'edit'

],

'*' => [

'controller' => 'MyApp\Controller\IndexController',

'action' => 'error'

]

]

];

Then you can use include to push the configuration array into the application object.

The application object will parse the routes array and register those routes with the application.

index.php

$app = new Pop\Application(include __DIR__ . '/config/application.php');

$app->run();

The Router Object

The router object is one of the main components of a Pop application. It serves as the gatekeeper

that routes requests to their proper controller.

With the application.php config above, the actions listed will be routed to methods within the

MyApp\Controller\IndexController object, index(), users(), edit($id) and error() respectively.

The route '/users[/]' allows for an optional trailing slash. The route '/edit/:id' is expecting a value

that will populate the variable $id that will be passed into the edit($id) method, such as '/edit/1001'.

Failure to have the ID segment of the URL will result in an non-match, or invalid route.

If you don't want to be so strict about the parameters passed into a method or function, you can make

the parameter optional like this: '/edit[/:id]'. The respective method would then look like this:

edit($id = null).

Here is a list of possible route options for web applications:

Web Route

What's Expected

/foo/:bar/:baz

All 3 params are required

/foo[/:bar][/:baz]

First param required, last two are optional

/foo/:bar[/:baz]

First two params required, last one is optional

/foo/:bar/:baz[/:some][/:other]

Two required, two optional

/foo/:bar/:baz*

One required param, one required param that is a collection (array)

/foo/:bar[/:baz*]

One required param, one optional param that is a collection (array)

And here is a list of possible route options for CLI applications:

CLI Route

What's Expected

foo bar

All 2 params are required

foo [bar|baz]

First param required, 2nd param has optional 2 values

foo -o1 [-o2]

First param required, 1st option required, 2nd option optional

foo --option1|-o1 [--option2|-o2]

First param required, 1st option required, 2nd option optional

foo []

First param required, 1st value required, 2nd value optional

foo --name= [--email=]

First param required, 1st opt value required, 2nd opt value optional

Routing for a CLI application

application.php

return [

'routes' => [

'help' => [

'controller' => 'MyApp\Controller\IndexController',

'action' => 'help'

],

'hello ' => [

'controller' => 'MyApp\Controller\IndexController',

'action' => 'hello'

]

]

];

app.php

$app = new Pop\Application(include __DIR__ . '/config/application.php');

$app->run();

As before, the actions listed in the application.php config above will be routed to methods within the

MyApp\Controller\IndexController object, help() and hello($name) respectively.

Dynamic Routing

There is support for dynamic routing for both web and CLI applications. The reserved route keywords

controller and action are used to map the route to a matched controller class and respective

action method within that class. You could define a dynamic web route like this:

return [

'routes' => [

'/:controller/:action[/:param]' => [

'prefix' => 'MyApp\Controller\\'

]

]

];

which will map a route like

/users/edit/1001

MyApp\Controller\UsersController->edit($id)

A dynamic CLI route like would work in a similar fashion:

return [

'routes' => [

'foo []' => [

'prefix' => 'MyApp\Controller\\'

]

]

];

which will map a route like

foo users edit 1001

MyApp\Controller\UsersController->edit($id)

The Controller Object

The controller object is the 'C' in the MVC design pattern and gives you the ability to encapsulate

the behavior and functionality of how the routes behave and are handled. But it should be noted that

you don't have to use a full controller object. For smaller applications, you can use anything that is

callable, like a closure. An example of that would be:

use Pop\Application;

use Pop\Router\Router;

$routes = [

'/hello' => [

'controller' => function() {

echo 'Hello World';

}

],

'/hello/:name' => [

'controller' => function($name) {

echo 'Hello ' . $name;

}

]

];

$app = new Application(new Router($routes));

$app->run();

But, for most larger applications, it would be best to use a full controller object to manage the

overall behavior or what is to happen for specific routes. The base controller object is an abstract

controller class Pop\Controller\AbstractController, which implements Pop\Controller\ControllerInterface.

The base functionality is fairly simple and allows you to build and structure your controller as needed.

The only base functionality wired in is a dispatch method that handles the actual dispatching of

the appropriate method and also the default action methods to set up what happens with a route/method

isn't matched (typically used for error handling.)

Let's take a look at what the MyApp\Controller\IndexController class from the above web example

might look like:

namespace MyApp\Controller;

use Pop\Controller\AbstractController;

class IndexController extends AbstractController

{

public function index()

{

// Do something for the index page

}

public function users()

{

// Do something for the users page

}

public function edit($id)

{

// Edit user with $id

}

public function error()

{

// Handle a non-match route request

}

}

The Model Object

The model object is the 'M' in the MVC design pattern and gives you the ability to map your data to

an object that can be consumed and utilized by the other parts of you application. An abstract model

class is provided, Pop\Model\AbstractModel, and it represents a basic data object the acts more or

less like any array or value object. It has a single property data, implements ArrayAccess,

Countable and IteratorAggregate. Once you extend the abstract model class, you build in the logic

needed to handle the business logic in your application.

namespace MyApp\Model;

use Pop\Model\AbstractModel;

class User extends AbstractModel

{

public function getById($id)

{

// Perform the logic to get a user by $id

}

}

The Module Manager

The module manager provides a way to extend the core functionality of your application. The module manager

object is really a collection object of actual module objects that serves as the bridge to integrate the

modules with the application. You can think of the module objects themselves as "mini application objects"

because, like the application object, they can take a configuration array that will wire up routes and other

settings specific to the module.

Here's an example of a way to inject a module into an application. You'll want to register the autoloader

with the application so that it can register the modules with the application.

// Using Composer's autoloader

$autoloader = require __DIR__ . APP_PATH . '/vendor/autoload.php';

$app = new Pop\Application($autoloader, include __DIR__ . '/config/application.php');

// $myModuleConfig contains the config settings for the

// module, such the autoload prefix and the routes

$app->register('MyModule', $myModuleConfig);

The $myModuleConfig will be injected into a basic module object and registered with the application.

If you wish to have your own module object with customized configuration and functionality, you can

inject that directly:

$app->register('MyModule', new MyModule\Module($app));

The Event Manager

The event manager provides a way to hook specific events and functionality into certain points in the

application's life cycle. The default hook points with the application object are:

app.init

app.route.pre

app.dispatch.pre

app.dispatch.post

app.error

You can simply register callable objects with the event manager to have them be called at that time

in the application's life cycle:

$app->on('app.route.pre', function($application) {

// Do some pre-route stuff

});

The Service Locator

The service locator provides a way to make common services available throughout the application's

life cycle. You can set them up at the beginning of the application and call them any time during

the application's life cycle.

$app->setService('foo', 'MyApp\FooService');

Inside of a controller object:

namespace MyApp\Controller;

use Pop\Controller\AbstractController;

class IndexController extends AbstractController

{

public function index()

{

$foo = $this->application->getService('foo');

// Do something with the 'foo' service

}

}

Configuration Tips

You've seen in the above examples that both the application and module config arrays can have

a 'routes' key set that defines the routes of the application or module. Additionally, the keys

'events' and 'services' are allowed as well, so you can wire up your application and module

all from the configuration array:

return [

'routes' => [

'/' => [

'controller' => 'MyApp\Controller\IndexController',

'action' => 'index'

],

'/users[/]' => [

'controller' => 'MyApp\Controller\IndexController',

'action' => 'users'

],

'/edit/:id' => [

'controller' => 'MyApp\Controller\IndexController',

'action' => 'edit'

],

'*' => [

'controller' => 'MyApp\Controller\IndexController',

'action' => 'error'

]

],

'services' => [

'session' => [

'call' => 'Pop\Session\Session::getInstance'

]

],

'events' => [

[

'name' => 'app.route.post',

'action' => 'MyApp\Event\Foo::bootstrap',

'priority' => 1000

]

]

];

The module config also supports the keys 'prefix', 'psr-0' and 'src' for autoloading purposes.

The default is to autoload with PSR-4, unless the 'psr-0' key is set to true.

return [

'prefix' => 'MyModule\\',

'src' => __DIR__ . '/../src',

];

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值