Cherrycake
ExamplesGithub
version 2.x alpha
version 2.x alpha
  • Introduction
  • Status
  • Changelog
  • Migration
  • Architecture
    • Basics
    • Modules
    • Classes
    • Lifecycle
      • Deep lifecycle
    • Performance
    • Security
    • Patterns
      • Files structure
    • Items
    • Server requirements
  • Guide
    • Getting started
      • Skeleton start
      • Docker start
    • Modules guide
    • Classes guide
    • Actions guide
      • Complex actions
      • Variable path components
      • Accept GET or POST parameters
      • Getting the URL of an action
      • Cached actions
      • Brute force attacks
    • Patterns guide
      • Passing variables to a pattern
      • Nested patterns
      • Cached patterns
    • Cache guide
      • Time To Live
      • Using cache
      • Lists
      • Queues
      • Pools
    • Database guide
      • Basic queries
      • Prepared queries
      • Cached queries
      • Cache key naming
      • Removing queries from cache
    • Items guide
      • Item cache
      • Item lists
      • Items custom filters
      • Items custom ordering
      • Mixing filters and ordering
      • Items with relationships
      • Items cache
    • HtmlDocument guide
    • Css and Javascript guide
      • Modules injecting CSS and JavaScript
    • Session guide
    • Login guide
      • Creating a complete login workflow
    • Locale guide
      • Multilingual texts
      • Domain based site localization
    • Log guide
      • Loading Log events from the database
    • Stats guide
      • Stats events with additional dimensions
      • Loading Stats events from the database
    • Janitor guide
      • Janitor tasks configuration files
    • Command line interface
    • Debugging
  • Reference
    • Core modules
      • Actions
        • Actions methods
      • Browser
      • Cache
        • Cache methods
      • Css
        • Css methods
      • Database
      • Email
      • Errors
      • HtmlDocument
        • HtmlDocument methods
      • ItemAdmin
      • Janitor
        • Janitor methods
      • Javascript
        • Javascript methods
      • Locale
        • Locale methods
      • Log
        • Log methods
      • Login
        • Login methods
      • Output
        • Output methods
      • Patterns
        • Patterns methods
      • Security
        • Security methods
      • Session
        • Session methods
      • Stats
        • Stats methods
      • SystemLog
      • TableAdmin
      • Translation
      • Validate
    • Core classes
      • Action
        • Action methods
        • Action properties
      • AjaxResponseJson
      • BasicObject
        • BasicObject methods
      • CacheProvider
        • CacheProvider methods
      • Color
      • DatabaseProvider
        • DatabaseProvider methods
      • DatabaseResult
        • DatabaseResult methods
        • DatabaseResult properties
      • DatabaseRow
      • Engine
        • Engine methods
        • Engine properties
      • Gradient
      • Item
        • Item methods
        • Item properties
      • Items
        • Items methods
        • Items properties
      • Image
      • JanitorTask
        • JanitorTask methods
        • JanitorTask properties
      • LogEvent
        • LogEvent methods
        • LogEvent Properties
      • LogEvents
        • LogEvents methods
      • Module
        • Module methods
        • Module properties
      • Response
      • Request
        • Request methods
      • RequestParameter
        • RequestParameter methods
      • RequestPathComponent
        • RequestPathComponent methods
      • Result
      • StatsEvent
        • StatsEvent properties
      • StatsEvents
        • StatsEvents methods
      • SystemLogEvent
        • SystemLogEvent methods
        • SystemLogEvent properties
      • SystemLogEvents
        • SystemLogEvents methods
  • Code conventions
  • License
  • Extras
Powered by GitBook
On this page

Was this helpful?

  1. Architecture
  2. Lifecycle

Deep lifecycle

Let's take a deep dive on a typical request lifecycle.

PreviousLifecycleNextPerformance

Last updated 4 years ago

Was this helpful?

To deeper understand the lifecycle of a request, we'll use the same example as in the section, but this time we'll stop and see with greater detail everything that happens behind the scenes, this will give you a better understanding of the Cherrycake architecture.

If you'd rather prefer to start working with Cherrycake and skip this section about the inner workings of Cherrycake, go straight to the guide, or keep on learning about the Cherrycake architecture in the section.

When a request is received, the index.php file in your App's public directory is executed. This is the entry point for all requests to your Cherrycake application, and all it does is loading Cherrycake, initialize it and call the method. This looks something like this:

namespace CherrycakeApp;
require "vendor/tin-cat/cherrycake-engine/load.php"

$e = new \Cherrycake\Engine;

if ($e->init(__NAMESPACE__, [
    "baseCoreModules" => ["Actions"]
]))
    $e->attendWebRequest();

$e->end();

When the engine is initialized with , it loads and initializes the modules specified in baseCoreModules. Since the modules is the one in charge of receiving and handling requests, you should at least specify this module on the list.

The default value for the baseCoreModules key is ["Actions"], so if you only need the Actions module like in our example, you can skip this key on the hash array and it will be included automatically. In the example, this means we can simplify the line to just $e->init(__NAMESPACE__)

During its initialization, the module loops through all available modules and asks them to map whatever actions they might need. It does so by using the method, which goes through all the available modules and executes the specified static method name, like this:

$e->callMethodOnAllModules("mapActions");

To optimize performance, the method caches the information about which methods are available in modules so it doesn't need to search for those methods each time a request is made.

public static function mapActions() {
	global $e;
	$e->Actions->mapAction(
		"homePage",
		new \Cherrycake\Action([
			"moduleType" => \Cherrycake\ACTION_MODULE_TYPE_APP,
			"moduleName" => "Home",
			"methodName" => "homePage",
			"request" => new \Cherrycake\Request([
				"pathComponents" => false,
				"parameters" => false
			])
		])
	);
}
$this->Actions->run($_SERVER["REQUEST_URI"]);

Notice that this action matches our example request of the home page (/ path) because it specifically has no pathComponents

var $dependentCoreModules = [
    "Patterns"
];
function homePage() {
    global $e;
    $e->Patterns->out("Home/Home.html");
    return true;
}
$e->Output->setResponse(new \Cherrycake\ResponseTextHtml([
			"code" => $code,
			"payload" => $this->parse($patternName, $setup)
]));

All mapActions methods found in any of the available modules (both core and app modules) are executed, so any module that needs to map an action to respond to requests must do it so on its mapActions static method by calling the method. In our Home example module, this would look like this:

Now that we have all the possible actions mapped, the call to in index.php asks the module to find and run the action that matches the current request URI. This is how this request to the module looks internally:

Since the browser in our example has requested the root page of our website, the module searches all the mapped actions for one that matches the current "/" request, and finds the action named "homePage".

In the declaration of this the moduleName and methodName keys are used to specify which module::method should be called when the action is executed. In our example, Home::homePage.

Cherrycake provides a request-level cache. At this point, if the requested has been cached, the result is obtained from cache and the execution ends here.

The Home module will use the module to retrieve an HTML file and send it back to the browser, this is why this dependency is specified on the dependentCoreModules property of Home, like this:

Now Home::homePage uses the method to send the HTML file to the browser, like this:

In turn, depends on the module, which was loaded and initialized automatically as soon as the chain of dependencies started, when our Home module was loaded.

Since is actually a parser, it not only loads the HTML file, but also parses it using and then sends the result as a object to , like this:

When the execution is about to end, the calls the end method on all loaded modules. The calls on its end method, causing the parsed HTML file to be sent to the browser and concluding the request lifecycle.

Actions
Action
Action
Patterns
Patterns
Output
Lifecycle
Getting started
Performance
Actions
Actions
Actions
Actions
Patterns
ResponseTextHtml
Engine
Output
Engine::attendWebRequest
Engine::init
Engine::init
Engine::callMethodOnAllModules
Engine::callMethodOnAllModules
Engine::attendWebRequest
Actions::mapAction
Patterns::out
Patterns:parse
Output::setResponse
Output::sendResponse