From 0c4018ec88e25fcd1d8d71a6172c32d64a6229ad Mon Sep 17 00:00:00 2001 From: Taylor Otwell Date: Wed, 21 Sep 2011 21:46:16 -0500 Subject: [PATCH] refactoring. --- .gitignore | 1 + application/config/aliases.php | 10 +- application/config/error.php | 79 +++++- application/filters.php | 2 +- application/views/error/404.php | 125 ++++----- application/views/error/500.php | 120 +++----- application/views/error/exception.php | 153 +++++------ application/views/home/index.php | 161 ++++++----- laravel/arr.php | 47 +--- laravel/asset.php | 59 ---- laravel/benchmark.php | 2 - laravel/{ => bootstrap}/core.php | 10 +- laravel/bootstrap/errors.php | 73 +++++ laravel/config.php | 70 +---- laravel/config/container.php | 70 ++++- laravel/container.php | 64 +---- laravel/controller.php | 15 +- laravel/cookie.php | 50 ++-- laravel/facades.php | 6 +- laravel/file.php | 38 ++- laravel/form.php | 87 +----- laravel/html.php | 93 ------- laravel/inflector.php | 8 - laravel/input.php | 121 +++----- laravel/lang.php | 41 +-- laravel/laravel.php | 43 +-- laravel/loader.php | 17 -- laravel/redirect.php | 29 -- laravel/request.php | 97 +++---- laravel/response.php | 37 --- laravel/routing/loader.php | 6 - laravel/routing/router.php | 17 +- laravel/security/auth.php | 13 +- laravel/session/drivers/cookie.php | 20 +- laravel/session/manager.php | 8 +- laravel/session/transporters/cookie.php | 24 +- laravel/uri.php | 57 ++-- laravel/url.php | 52 +--- laravel/validation/messages.php | 30 -- laravel/validation/validator.php | 2 +- laravel/view.php | 349 +++++++++++++++--------- public/index.php | 4 +- 42 files changed, 980 insertions(+), 1330 deletions(-) create mode 100644 .gitignore rename laravel/{ => bootstrap}/core.php (91%) create mode 100644 laravel/bootstrap/errors.php diff --git a/.gitignore b/.gitignore new file mode 100644 index 00000000..b017e3c3 --- /dev/null +++ b/.gitignore @@ -0,0 +1 @@ +favicon.* \ No newline at end of file diff --git a/application/config/aliases.php b/application/config/aliases.php index 8c184453..49d67d6b 100644 --- a/application/config/aliases.php +++ b/application/config/aliases.php @@ -25,7 +25,7 @@ 'Cache' => 'Laravel\\Cache', 'Config' => 'Laravel\\Config', 'Controller' => 'Laravel\\Controller', - 'Cookie' => 'Laravel\\Cookie', + 'Cookie' => 'Laravel\\Facades\\Cookie', 'Crypter' => 'Laravel\\Facades\\Crypter', 'DB' => 'Laravel\\Database\\Manager', 'Eloquent' => 'Laravel\\Database\\Eloquent\\Model', @@ -34,20 +34,20 @@ 'Hasher' => 'Laravel\\Facades\\Hasher', 'HTML' => 'Laravel\\HTML', 'Inflector' => 'Laravel\\Inflector', - 'Input' => 'Laravel\\Input', + 'Input' => 'Laravel\\Facades\\Input', 'IoC' => 'Laravel\\IoC', 'Lang' => 'Laravel\\Lang', 'Loader' => 'Laravel\\Loader', 'Messages' => 'Laravel\\Validation\\Messages', 'Package' => 'Laravel\\Facades\\Package', - 'URI' => 'Laravel\\URI', + 'URI' => 'Laravel\\Facades\\URI', 'URL' => 'Laravel\\URL', 'Redirect' => 'Laravel\\Redirect', - 'Request' => 'Laravel\\Request', + 'Request' => 'Laravel\\Facades\\Request', 'Response' => 'Laravel\\Response', 'Session' => 'Laravel\\Facades\\Session', 'Str' => 'Laravel\\Str', - 'Validator' => 'Laravel\\Validator', + 'Validator' => 'Laravel\\Validation\\Validator', 'View' => 'Laravel\\View', ); \ No newline at end of file diff --git a/application/config/error.php b/application/config/error.php index 721b4064..017f1720 100644 --- a/application/config/error.php +++ b/application/config/error.php @@ -2,12 +2,83 @@ return array( + /* + |-------------------------------------------------------------------------- + | Error Detail + |-------------------------------------------------------------------------- + | + | Detailed error messages contain information about the file in which + | an error occurs, a stack trace, and a snapshot of the source code + | in which the error occured. + | + | If your application is in production, consider turning off error details + | for enhanced security and user experience. + | + */ + + 'detail' => true, + + /* + |-------------------------------------------------------------------------- + | Error Logging + |-------------------------------------------------------------------------- + | + | Error Logging will use the "logger" function defined below to log error + | messages, which gives you complete freedom to determine how error + | messages are logged. Enjoy the flexibility. + | + */ + + 'log' => false, + /* |-------------------------------------------------------------------------- | Error Handler |-------------------------------------------------------------------------- | | Because of the various ways of managing error logging, you get complete + | flexibility in Laravel to manage error logging as you see fit. + | + | This function will be called when an error occurs in your application. + | You can log the error however you like. + | + | The error "severity" passed to the method is a human-readable severity + | level such as "Parsing Error" or "Fatal Error". + | + | A simple logging system has been setup for you. By default, all errors + | will be logged to the storage/log.txt file. + | + */ + + 'handler' => function($exception, $severity, $message, $config) + { + if ($config['detail']) + { + $data = compact('exception', 'severity', 'message'); + + $response = Response::view('error.exception', $data)->status(500); + } + else + { + $response = Response::error('500'); + } + + if ($config['log']) + { + call_user_func($config['logger'], $severity, $message); + } + + $response->send(); + + exit(1); + }, + + /* + |-------------------------------------------------------------------------- + | Error Logger + |-------------------------------------------------------------------------- + | + | Because of the various ways of managing error logging, you get complete | flexibility to manage error logging as you see fit. | | This function will be called when an error occurs in your application. @@ -21,11 +92,9 @@ | */ - 'handler' => function($exception) + 'logger' => function($severity, $message) { - var_dump($exception); - - exit(1); - }, + File::append(STORAGE_PATH.'log.txt', date('Y-m-d H:i:s').' '.$severity.' - '.$message.PHP_EOL); + } ); \ No newline at end of file diff --git a/application/filters.php b/application/filters.php index 5150cf5c..a2d87a30 100644 --- a/application/filters.php +++ b/application/filters.php @@ -56,7 +56,7 @@ 'auth' => function() { - return ( ! Auth::make()->check()) ? Redirect::to_login() : null; + return ( ! Auth::check()) ? Redirect::to('login') : null; }, diff --git a/application/views/error/404.php b/application/views/error/404.php index 089a00f3..4513dbe0 100644 --- a/application/views/error/404.php +++ b/application/views/error/404.php @@ -1,87 +1,64 @@ - + - - - 404 - Not Found + + - - - + Error 404 - Not Found - + + +
+ - #wrapper h2:first-of-type { - margin-top: 0; - } - - - - +

We're really sorry, but we couldn't find the resource you requested.

-
- - -

- -

We couldn't find the resource you requested. Would you like go to our home page instead?

-
- +

Perhaps you would like to go to our instead?

+
+ \ No newline at end of file diff --git a/application/views/error/500.php b/application/views/error/500.php index 4e0ee733..fefb6aea 100644 --- a/application/views/error/500.php +++ b/application/views/error/500.php @@ -1,87 +1,55 @@ - + - - - 500 - Internal Server Error + + - - - + Error 500 - Internal Server Error - + + +
+ - #header { - margin: 0 auto; - margin-bottom: 15px; - margin-top: 20px; - width: 80%; - } +

- #wrapper { - background-color: #fff; - border-radius: 10px; - margin: 0 auto; - padding: 10px; - width: 80%; - } +

We're really sorry, but something went wrong while we were processing your request.

- #wrapper h2:first-of-type { - margin-top: 0; - } - - - - - -
- - -

- -

Something failed while we were handling your request. Would you like go to our home page instead?

-
- +

Perhaps you would like to go to our instead?

+
+ \ No newline at end of file diff --git a/application/views/error/exception.php b/application/views/error/exception.php index 15990ec1..a1aac7e9 100644 --- a/application/views/error/exception.php +++ b/application/views/error/exception.php @@ -1,102 +1,89 @@ - + - - - Laravel - <?php echo $severity; ?> - - - - + + - + + +
+

- #wrapper h2:first-of-type { - margin-top: 0; - } - - - - +

Message

-
-

Message:

+
-

+

Stack Trace

-

Stack Trace:

+
getTraceAsString(); ?>
-
+

Snapshot

-

Snapshot:

+ - 0): ?> + foreach (File::snapshot($exception->getFile(), $exception->getLine()) as $num => $context) + { + $lines[] = $num.': '.$context; + } + ?> - $context): ?> -
- - - - Snapshot Unavailable. - -

-
- +
+
+ \ No newline at end of file diff --git a/application/views/home/index.php b/application/views/home/index.php index 6f8a0371..3c51d86b 100644 --- a/application/views/home/index.php +++ b/application/views/home/index.php @@ -1,79 +1,108 @@ - + - - - Welcome To Laravel! - - - - + + - - - - + #main p { + line-height: 25px; + margin: 10px 0; + } -
-

Installation Complete!

+ #main pre { + background-color: #f0f0f0; + border-left: 1px solid #d8d8d8; + border-top: 1px solid #d8d8d8; + border-radius: 5px; + padding: 10px; + } -

Ready to dig in? Start building your application in the application/routes.php file.

+ #main ul { + margin: 10px 0; + padding: 0 30px; + } -

Need to learn more? Peruse our wonderful documentation.

-
- + #main li { + margin: 5px 0; + } + + + +
+

Welcome to Laravel

+ +

+ You have successfully installed the Laravel framework. Laravel is a simple framework + to help web artisans create beautiful, creative applications using elegant, expressive + syntax. You'll love using it. +

+ +

Learn the terrain.

+ +

+ You've landed yourself on our default home page. The route that + is generating this page lives at: +

+ +
APP_PATH/routes.php
+ +

And the view sitting before you can be found at:

+ +
APP_PATH/views/home/index.php
+ +

Create something beautiful.

+ +

+ Now that you're up and running, it's time to start creating! + Here are some links to help you get started: +

+ + + +
+ \ No newline at end of file diff --git a/laravel/arr.php b/laravel/arr.php index 61a0e1fb..349a1929 100644 --- a/laravel/arr.php +++ b/laravel/arr.php @@ -7,18 +7,6 @@ class Arr { /** * Get an item from an array. * - * This method supports accessing arrays through JavaScript "dot" style syntax - * for conveniently digging deep into nested arrays. Like most other Laravel - * "get" methods, a default value may be provided. - * - * - * // Get the value of $array['user']['name'] - * $value = Arr::get($array, 'user.name'); - * - * // Get a value from the array, but return a default if it doesn't exist - * $value = Arr::get($array, 'user.name', 'Taylor'); - * - * * @param array $array * @param string $key * @param mixed $default @@ -44,16 +32,7 @@ public static function get($array, $key, $default = null) /** * Set an array item to a given value. * - * This method supports accessing arrays through JavaScript "dot" style syntax - * for conveniently digging deep into nested arrays. - * - * - * // Set the $array['user']['name'] value in the array - * Arr::set($array, 'user.name', 'Taylor'); - * - * // Set the $array['db']['driver']['name'] value in the array - * Arr::set($array, 'db.driver.name', 'SQLite'); - * + * The same "dot" syntax used by the "get" method may be used here. * * @param array $array * @param string $key @@ -84,20 +63,6 @@ public static function set(&$array, $key, $value) /** * Return the first element in an array which passes a given truth test. * - * The truth test is passed as a closure, and simply returns true or false. - * The array key and value will be passed to the closure on each iteration. - * - * Like the "get" method, a default value may be specified, and will be - * returned if no matching array elements are found by the method. - * - * - * // Get the first string from an array with a length of 3 - * $value = Arr::first($array, function($k, $v) {return strlen($v) == 3;}); - * - * // Return a default value if no matching array elements are found - * $value = Arr::first($array, function($k, $v) {return;}, 'Default'); - * - * * @param array $array * @param Closure $callback * @return mixed @@ -113,15 +78,7 @@ public static function first($array, $callback, $default = null) } /** - * Remove all values in the array that are contained within a given array of values. - * - * - * // Remove all empty string values from an array - * $array = Arr::without($array, array('')); - * - * // Remove all array values that are "3", "2", or "1" - * $array = Arr::without($array, array(3, 2, 1)); - * + * Remove all array values that are contained within a given array of values. * * @param array $array * @param array $without diff --git a/laravel/asset.php b/laravel/asset.php index e043a356..f2675e2f 100644 --- a/laravel/asset.php +++ b/laravel/asset.php @@ -12,18 +12,6 @@ class Asset { /** * Get an asset container instance. * - * If no container name is specified, the default container will be returned. - * Containers provide a convenient method of grouping assets while maintaining - * expressive code and a clean API. - * - * - * // Get an instance of the default asset container - * $container = Asset::container(); - * - * // Get an instance of the "footer" container - * $container = Asset::container('footer'); - * - * * @param string $container * @return Asset_Container */ @@ -39,14 +27,6 @@ public static function container($container = 'default') /** * Magic Method for calling methods on the default Asset container. - * - * - * // Call the "add" method on the default asset container - * Asset::add('jquery', 'js/jquery.js'); - * - * // Get all of the styles from the default container - * echo Asset::styles(); - * */ public static function __callStatic($method, $parameters) { @@ -90,21 +70,6 @@ public function __construct($name) * asset being registered (CSS or JavaScript). If you are using a non-standard * extension, you may use the style or script methods to register assets. * - * You may also specify asset dependencies. This will instruct the class to - * only link to the registered asset after its dependencies have been linked. - * For example, you may wish to make jQuery UI dependent on jQuery. - * - * - * // Add an asset to the container - * Asset::container()->add('style', 'style.css'); - * - * // Add an asset to the container with attributes - * Asset::container()->add('style', 'style.css', array(), array('media' => 'print')); - * - * // Add an asset to the container with dependencies - * Asset::container()->add('jquery', 'jquery.js', array('jquery-ui')); - * - * * @param string $name * @param string $source * @param array $dependencies @@ -121,17 +86,6 @@ public function add($name, $source, $dependencies = array(), $attributes = array /** * Add a CSS file to the registered assets. * - * - * // Add a CSS file to the registered assets - * Asset::container()->style('common', 'common.css'); - * - * // Add a CSS file with dependencies to the registered assets - * Asset::container()->style('common', 'common.css', array('reset')); - * - * // Add a CSS file with attributes to the registered assets - * Asset::container()->style('common', 'common.css', array(), array('media' => 'print')); - * - * * @param string $name * @param string $source * @param array $dependencies @@ -153,17 +107,6 @@ public function style($name, $source, $dependencies = array(), $attributes = arr /** * Add a JavaScript file to the registered assets. * - * - * // Add a CSS file to the registered assets - * Asset::container()->script('jquery', 'jquery.js'); - * - * // Add a CSS file with dependencies to the registered assets - * Asset::container()->script('jquery', 'jquery.js', array('jquery-ui')); - * - * // Add a CSS file with attributes to the registered assets - * Asset::container()->script('loader', 'loader.js', array(), array('defer')); - * - * * @param string $name * @param string $source * @param array $dependencies @@ -180,8 +123,6 @@ public function script($name, $source, $dependencies = array(), $attributes = ar /** * Add an asset to the array of registered assets. * - * Assets are organized in the array by type (CSS or JavaScript). - * * @param string $type * @param string $name * @param string $source diff --git a/laravel/benchmark.php b/laravel/benchmark.php index 78bec360..a0d29f3c 100644 --- a/laravel/benchmark.php +++ b/laravel/benchmark.php @@ -12,8 +12,6 @@ class Benchmark { /** * Start a benchmark starting time. * - * The elapsed time since setting a benchmark may checked via the "check" method. - * * @param string $name * @return void */ diff --git a/laravel/core.php b/laravel/bootstrap/core.php similarity index 91% rename from laravel/core.php rename to laravel/bootstrap/core.php index 200c74c0..2ee219ae 100644 --- a/laravel/core.php +++ b/laravel/bootstrap/core.php @@ -1,9 +1,10 @@ 'Error', + E_ERROR => 'Error', + E_WARNING => 'Warning', + E_PARSE => 'Parsing Error', + E_NOTICE => 'Notice', + E_CORE_ERROR => 'Core Error', + E_CORE_WARNING => 'Core Warning', + E_COMPILE_ERROR => 'Compile Error', + E_COMPILE_WARNING => 'Compile Warning', + E_USER_ERROR => 'User Error', + E_USER_WARNING => 'User Warning', + E_USER_NOTICE => 'User Notice', + E_STRICT => 'Runtime Notice', + ); + + $file = str_replace(array(APP_PATH, SYS_PATH), array('APP_PATH/', 'SYS_PATH/'), $e->getFile()); + + $message = rtrim($e->getMessage(), '.').' in '.$file.' on line '.$e->getLine().'.'; + + $severity = (array_key_exists($e->getCode(), $levels)) ? $levels[$e->getCode()] : $e->getCode(); + + return array($severity, $message); +}; + +/** + * Create the exception handler function. All of the handlers registered + * with PHP will call this handler when an error occurs, giving us a common + * spot to put error handling logic. + */ +$handler = function($e) use ($formatter) +{ + list($severity, $message) = $formatter($e); + + call_user_func(Config::get('error.handler'), $e, $severity, $message, Config::get('error')); +}; + +/** + * Register the exception, error, and shutdown error handlers. + */ +set_exception_handler(function($e) use ($handler) +{ + $handler($e); +}); + +set_error_handler(function($number, $error, $file, $line) use ($handler) +{ + $handler(new \ErrorException($error, $number, 0, $file, $line)); +}); + +register_shutdown_function(function() use ($handler) +{ + if ( ! is_null($error = error_get_last())) + { + $handler(new \ErrorException($error['message'], $error['type'], 0, $error['file'], $error['line'])); + } +}); + +/** + * Set the error reporting and display levels. + */ +error_reporting(-1); + +ini_set('display_errors', 'Off'); \ No newline at end of file diff --git a/laravel/config.php b/laravel/config.php index d951a0fa..73f25cd2 100644 --- a/laravel/config.php +++ b/laravel/config.php @@ -32,14 +32,6 @@ public static function paths($paths) /** * Determine if a configuration item or file exists. * - * - * // Determine if the "options" configuration file exists - * $options = Config::has('options'); - * - * // Determine if a specific configuration item exists - * $timezone = Config::has('application.timezone'); - * - * * @param string $key * @return bool */ @@ -51,25 +43,6 @@ public static function has($key) /** * Get a configuration item. * - * Configuration items are stored in the application/config directory, and provide - * general configuration options for a wide range of Laravel facilities. - * - * The arrays may be accessed using JavaScript style "dot" notation to drill deep - * intot he configuration files. For example, asking for "database.connectors.sqlite" - * would return the connector closure for SQLite stored in the database configuration - * file. If no specific item is specfied, the entire configuration array is returned. - * - * Like most Laravel "get" functions, a default value may be provided, and it will - * be returned if the requested file or item doesn't exist. - * - * - * // Get the "timezone" option from the application config file - * $timezone = Config::get('application.timezone'); - * - * // Get an option, but return a default value if it doesn't exist - * $value = Config::get('some.option', 'Default'); - * - * * @param string $key * @param string $default * @return array @@ -83,10 +56,7 @@ public static function get($key, $default = null) return ($default instanceof \Closure) ? call_user_func($default) : $default; } - if (is_null($key)) - { - return static::$items[$file]; - } + if (is_null($key)) return static::$items[$file]; return Arr::get(static::$items[$file], $key, $default); } @@ -94,21 +64,6 @@ public static function get($key, $default = null) /** * Set a configuration item. * - * Configuration items are stored in the application/config directory, and provide - * general configuration options for a wide range of Laravel facilities. - * - * Like the "get" method, this method uses JavaScript style "dot" notation to access - * and manipulate the arrays in the configuration files. Also, like the "get" method, - * if no specific item is specified, the entire configuration array will be set. - * - * - * // Set the "timezone" option in the "application" array - * Config::set('application.timezone', 'America/Chicago'); - * - * // Set the entire "session" configuration array - * Config::set('session', $array); - * - * * @param string $key * @param mixed $value * @return void @@ -119,26 +74,12 @@ public static function set($key, $value) static::load($file); - if (is_null($key)) - { - Arr::set(static::$items, $file, $value); - } - else - { - Arr::set(static::$items[$file], $key, $value); - } + (is_null($key)) ? Arr::set(static::$items, $file, $value) : Arr::set(static::$items[$file], $key, $value); } /** * Parse a configuration key and return its file and key segments. * - * Configuration keys follow a {file}.{key} convention. So, for example, the - * "session.driver" option refers to the "driver" option within the "session" - * configuration file. - * - * If no specific item is specified, such as when requested "session", null will - * be returned as the value of the key since the entire file is being requested. - * * @param string $key * @return array */ @@ -154,13 +95,6 @@ protected static function parse($key) /** * Load all of the configuration items from a module configuration file. * - * If the configuration file has already been loaded into the items array, there - * is no need to load it again, so "true" will be returned immediately. - * - * Configuration files cascade across directories. So, for example, if a configuration - * file is in the system directory, its options will be overriden by a matching file - * in the application directory. - * * @param string $file * @return bool */ diff --git a/laravel/config/container.php b/laravel/config/container.php index 3e6e3604..6cf2c9b9 100644 --- a/laravel/config/container.php +++ b/laravel/config/container.php @@ -14,6 +14,12 @@ }), + 'laravel.cookie' => array('singleton' => true, 'resolver' => function($c) + { + return new Cookie($_COOKIE); + }), + + 'laravel.crypter' => array('resolver' => function($c) { return new Security\Crypter(MCRYPT_RIJNDAEL_256, 'cbc', Config::get('application.key')); @@ -25,6 +31,64 @@ return new Security\Hashing\Bcrypt(8, false); }), + + 'laravel.input' => array('singleton' => true, 'resolver' => function($c) + { + $input = array(); + + switch ($c->resolve('laravel.request')->method()) + { + case 'GET': + $input = $_GET; + break; + + case 'POST': + $input = $_POST; + break; + + case 'PUT': + case 'DELETE': + if ($c->resolve('laravel.request')->spoofed()) + { + $input = $_POST; + } + else + { + parse_str(file_get_contents('php://input'), $input); + } + } + + unset($input[Request::spoofer]); + + return new Input($input, $_FILES); + }), + + + 'laravel.request' => array('singleton' => true, 'resolver' => function($c) + { + return new Request($c->resolve('laravel.uri'), $_SERVER, $_POST); + }), + + + 'laravel.uri' => array('singleton' => true, 'resolver' => function($c) + { + return new URI($_SERVER); + }), + + + 'laravel.view' => array('singleton' => true, 'resolver' => function($c) + { + require_once SYS_PATH.'view'.EXT; + + return new View_Factory($c->resolve('laravel.composer'), VIEW_PATH); + }), + + + 'laravel.composer' => array('singleton' => true, 'resolver' => function($c) + { + return new View_Composer(require APP_PATH.'composers'.EXT); + }), + /* |-------------------------------------------------------------------------- | Laravel Routing Components @@ -97,7 +161,7 @@ 'laravel.session.id' => array('singleton' => true, 'resolver' => function($c) { - return Cookie::get('laravel_session'); + return $c->resolve('laravel.cookie')->get('laravel_session'); }), @@ -111,7 +175,7 @@ 'laravel.session.transporter' => array('resolver' => function($c) { - return new Session\Transporters\Cookie; + return new Session\Transporters\Cookie($c->resolve('laravel.cookie')); }), @@ -123,7 +187,7 @@ 'laravel.session.cookie' => array('resolver' => function($c) { - return new Session\Drivers\Cookie($c->resolve('laravel.crypter')); + return new Session\Drivers\Cookie($c->resolve('laravel.crypter'), $c->resolve('laravel.cookie')); }), diff --git a/laravel/container.php b/laravel/container.php index 77d48819..3bff4545 100644 --- a/laravel/container.php +++ b/laravel/container.php @@ -12,17 +12,6 @@ class IoC { /** * Get the active container instance. * - * The container is set early in the request cycle and can be access here for - * use as a service locator if object injection is not practical. - * - * - * // Get the active container instance - * $container = IoC::container(); - * - * // Get the active container instance and call the resolve method - * $container = IoC::container()->resolve('instance'); - * - * * @return Container */ public static function container() @@ -32,14 +21,6 @@ public static function container() /** * Magic Method for calling methods on the active container instance. - * - * - * // Call the "resolve" method on the active container instance - * $instance = IoC::resolve('instance'); - * - * // Equivalent operation using the "container" method - * $instance = IoC::container()->resolve('instance'); - * */ public static function __callStatic($method, $parameters) { @@ -78,16 +59,6 @@ public function __construct($registry = array()) /** * Register an object and its resolver. * - * The resolver function is called when the registered object is requested. - * - * - * // Register an object in the container - * IoC::register('something', function($container) {return new Something;}); - * - * // Register an object in the container as a singleton - * IoC::register('something', function($container) {return new Something;}, true); - * - * * @param string $name * @param Closure $resolver * @return void @@ -111,13 +82,8 @@ public function registered($name) /** * Register an object as a singleton. * - * Singletons will only be instantiated the first time they are resolved. On subsequent - * requests for the object, the original instance will be returned. - * - * - * // Register an object in the container as a singleton - * IoC::singleton('something', function($container) {return new Something;}); - * + * Singletons will only be instantiated the first time they are resolved. + * On subsequent requests for the object, the original instance will be returned. * * @param string $name * @param Closure $resolver @@ -131,13 +97,8 @@ public function singleton($name, $resolver) /** * Register an instance as a singleton. * - * This method allows you to register an already existing object instance with the - * container to be managed as a singleton instance. - * - * - * // Register an instance with the IoC container - * IoC::instance('something', new Something); - * + * This method allows you to register an already existing object instance + * with the container to be managed as a singleton instance. * * @param string $name * @param mixed $instance @@ -151,15 +112,6 @@ public function instance($name, $instance) /** * Resolve an object. * - * The object's resolver will be called and its result will be returned. If the - * object is registered as a singleton and has already been resolved, the instance - * that has already been instantiated will be returned. - * - * - * // Get the "something" object out of the IoC container - * $something = IoC::resolve('something'); - * - * * @param string $name * @return mixed */ @@ -179,14 +131,6 @@ public function resolve($name) /** * Magic Method for resolving classes out of the IoC container. - * - * - * // Get the "something" instance out of the IoC container - * $something = IoC::container()->something; - * - * // Equivalent method of retrieving the instance using the resolve method - * $something = IoC::container()->resolve('something'); - * */ public function __get($key) { diff --git a/laravel/controller.php b/laravel/controller.php index 7a20b1fc..f4503bca 100644 --- a/laravel/controller.php +++ b/laravel/controller.php @@ -30,19 +30,14 @@ public function __call($method, $parameters) * First, "laravel." will be prefixed to the requested item to see if there is * a matching Laravel core class in the IoC container. If there is not, we will * check for the item in the container using the name as-is. - * - * - * // Resolve the "laravel.input" instance from the IoC container - * $input = $this->input; - * - * // Resolve the "mailer" instance from the IoC container - * $mongo = $this->mailer; - * - * */ public function __get($key) { - if (IoC::container()->registered($key)) + if (IoC::container()->registered("laravel.{$key}")) + { + return IoC::container()->resolve("laravel.{$key}"); + } + elseif (IoC::container()->registered($key)) { return IoC::container()->resolve($key); } diff --git a/laravel/cookie.php b/laravel/cookie.php index 254f1d01..669f0cf0 100644 --- a/laravel/cookie.php +++ b/laravel/cookie.php @@ -2,33 +2,43 @@ class Cookie { + /** + * The cookies for the current request. + * + * @var array + */ + protected $cookies; + + /** + * Create a new cookie manager instance. + * + * @param array $cookies + * @return void + */ + public function __construct(&$cookies) + { + $this->cookies =& $cookies; + } + /** * Determine if a cookie exists. * * @param string $name * @return bool */ - public static function has($name) + public function has($name) { - return ! is_null(static::get($name)); + return ! is_null($this->get($name)); } /** * Get the value of a cookie. * - * - * // Get the value of a cookie - * $value = Cookie::get('color'); - * - * // Get the value of a cookie or return a default value - * $value = Cookie::get('color', 'blue'); - * - * * @param string $name * @param mixed $default * @return string */ - public static function get($name, $default = null) + public function get($name, $default = null) { return Arr::get($_COOKIE, $name, $default); } @@ -44,9 +54,9 @@ public static function get($name, $default = null) * @param bool $http_only * @return bool */ - public static function forever($name, $value, $path = '/', $domain = null, $secure = false, $http_only = false) + public function forever($name, $value, $path = '/', $domain = null, $secure = false, $http_only = false) { - return static::put($name, $value, 2628000, $path, $domain, $secure, $http_only); + return $this->put($name, $value, 2628000, $path, $domain, $secure, $http_only); } /** @@ -58,14 +68,6 @@ public static function forever($name, $value, $path = '/', $domain = null, $secu * However, you simply need to pass the number of minutes for which you * wish the cookie to be valid. No funky time calculation is required. * - * - * // Create a cookie that exists until the user closes their browser - * Cookie::put('color', 'blue'); - * - * // Create a cookie that exists for 5 minutes - * Cookie::put('name', 'blue', 5); - * - * * @param string $name * @param string $value * @param int $minutes @@ -75,7 +77,7 @@ public static function forever($name, $value, $path = '/', $domain = null, $secu * @param bool $http_only * @return bool */ - public static function put($name, $value, $minutes = 0, $path = '/', $domain = null, $secure = false, $http_only = false) + public function put($name, $value, $minutes = 0, $path = '/', $domain = null, $secure = false, $http_only = false) { if (headers_sent()) return false; @@ -92,9 +94,9 @@ public static function put($name, $value, $minutes = 0, $path = '/', $domain = n * @param string $name * @return bool */ - public static function forget($name) + public function forget($name) { - return static::put($name, null, -60); + return $this->put($name, null, -60); } } \ No newline at end of file diff --git a/laravel/facades.php b/laravel/facades.php index 622e9515..668fc2e0 100644 --- a/laravel/facades.php +++ b/laravel/facades.php @@ -33,6 +33,10 @@ public static function __callStatic($method, $parameters) } class Auth extends Facade { public static $resolve = 'laravel.auth'; } +class Cookie extends Facade { public static $resolve = 'laravel.cookie'; } class Crypter extends Facade { public static $resolve = 'laravel.crypter'; } class Hasher extends Facade { public static $resolve = 'laravel.hasher'; } -class Session extends Facade { public static $resolve = 'laravel.session'; } \ No newline at end of file +class Input extends Facade { public static $resolve = 'laravel.input'; } +class Request extends Facade { public static $resolve = 'laravel.request'; } +class Session extends Facade { public static $resolve = 'laravel.session'; } +class URI extends Facade { public static $resolve = 'laravel.uri'; } \ No newline at end of file diff --git a/laravel/file.php b/laravel/file.php index 52731f32..58eeed14 100644 --- a/laravel/file.php +++ b/laravel/file.php @@ -119,13 +119,6 @@ public static function upload($key, $path, $files) /** * Get a file MIME type by extension. * - * If the MIME type can't be determined, "application/octet-stream" will be returned. - * - * - * // Returns 'application/x-tar' - * $mime = File::mime('path/to/file.tar'); - * - * * @param string $extension * @param string $default * @return string @@ -144,14 +137,6 @@ public static function mime($extension, $default = 'application/octet-stream') * * The Fileinfo PHP extension will be used to determine the MIME type of the file. * - * - * // Determine if a file is a JPG image - * $image = File::is('jpg', 'path/to/image.jpg'); - * - * // Determine if a file is any one of an array of types - * $image = File::is(array('jpg', 'png', 'gif'), 'path/to/image.jpg'); - * - * * @param array|string $extension * @param string $path * @return bool @@ -170,4 +155,27 @@ public static function is($extensions, $path) return false; } + /** + * Get the lines surrounding a given line in a file. + * + * @param string $path + * @param int $line + * @param int $padding + * @return array + */ + public static function snapshot($path, $line, $padding = 5) + { + if ( ! file_exists($path)) return array(); + + $file = file($path, FILE_IGNORE_NEW_LINES); + + array_unshift($file, ''); + + if (($start = $line - $padding) < 0) $start = 0; + + if (($length = ($line - $start) + $padding + 1) < 0) $length = 0; + + return array_slice($file, $start, $length, true); + } + } \ No newline at end of file diff --git a/laravel/form.php b/laravel/form.php index dd90bf0b..5cc723c1 100644 --- a/laravel/form.php +++ b/laravel/form.php @@ -19,17 +19,6 @@ class Form { * containing the request method. PUT and DELETE are not supported by HTML forms, so the * hidden field will allow us to "spoof" PUT and DELETE requests. * - * - * // Open a POST form to the current URI - * echo Form::open(); - * - * // Open a POST form to a given URI - * echo Form::open('user/profile'); - * - * // Open a PUT form to a given URI and add form attributes - * echo Form::open('user/profile', 'put', array('class' => 'profile')); - * - * * @param string $action * @param string $method * @param array $attributes @@ -75,7 +64,9 @@ protected static function method($method) */ protected static function action($action, $https) { - return HTML::entities(URL::to(((is_null($action)) ? Request::uri() : $action), $https)); + $uri = IoC::container()->resolve('laravel.uri')->get(); + + return HTML::entities(URL::to(((is_null($action)) ? $uri : $action), $https)); } /** @@ -158,14 +149,6 @@ public static function raw_token() /** * Create a HTML label element. * - * - * // Create a form label - * echo Form::label('email', 'E-Mail Address'); - * - * // Create a form label with attributes - * echo Form::label('email', 'E-Mail Address', array('class' => 'login')); - * - * * @param string $name * @param string $value * @param array $attributes @@ -184,17 +167,6 @@ public static function label($name, $value, $attributes = array()) * If an ID attribute is not specified and a label has been generated matching the input * element name, the label name will be used as the element ID. * - * - * // Create a "text" type input element - * echo Form::input('text', 'email'); - * - * // Create an input element with a specified value - * echo Form::input('text', 'email', 'example@gmail.com'); - * - * // Create an input element with attributes - * echo Form::input('text', 'email', 'example@gmail.com', array('class' => 'login')); - * - * * @param string $name * @param mixed $value * @param array $attributes @@ -327,14 +299,6 @@ public static function file($name, $attributes = array()) /** * Create a HTML textarea element. * - * - * // Create a textarea element - * echo Form::textarea('comment'); - * - * // Create a textarea with specified rows and columns - * echo Form::textarea('comment', '', array('rows' => 10, 'columns' => 50)); - * - * * @param string $name * @param string $value * @param array $attributes @@ -354,14 +318,6 @@ public static function textarea($name, $value = '', $attributes = array()) /** * Create a HTML select element. * - * - * // Create a selection element - * echo Form::select('sizes', array('S' => 'Small', 'L' => 'Large')); - * - * // Create a selection element with a given option pre-selected - * echo Form::select('sizes', array('S' => 'Small', 'L' => 'Large'), 'L'); - * - * * @param string $name * @param array $options * @param string $selected @@ -387,14 +343,6 @@ public static function select($name, $options = array(), $selected = null, $attr /** * Create a HTML checkbox input element. * - * - * // Create a checkbox element - * echo Form::checkbox('terms'); - * - * // Create a checkbox element that is checked by default - * echo Form::checkbox('terms', 'yes', true); - * - * * @param string $name * @param string $value * @param bool $checked @@ -409,14 +357,6 @@ public static function checkbox($name, $value = 1, $checked = false, $attributes /** * Create a HTML radio button input element. * - * - * // Create a radio button element - * echo Form::radio('apple'); - * - * // Create a radio button element that is selected by default - * echo Form::radio('microsoft', 'pc', true); - * - * * @param string $name * @param string $value * @param bool $checked @@ -450,14 +390,6 @@ protected static function checkable($type, $name, $value, $checked, $attributes) /** * Create a HTML submit input element. * - * - * // Create a submit input element - * echo Form::submit('Login!'); - * - * // Create a submit input element with attributes - * echo Form::submit('Login!', array('class' => 'login')); - * - * * @param string $value * @param array $attributes * @return string @@ -482,11 +414,6 @@ public static function reset($value, $attributes = array()) /** * Create a HTML image input element. * - * - * // Create an image input element - * echo Form::image('img/login.jpg'); - * - * * @param string $url * @param array $attributes * @return string @@ -501,14 +428,6 @@ public static function image($url, $name = null, $attributes = array()) /** * Create a HTML button element. * - * - * // Create a button input element - * echo Form::button('Login!'); - * - * // Create a button input element with attributes - * echo Form::button('Login!', array('class' => 'login')); - * - * * @param string $name * @param string $value * @param array $attributes diff --git a/laravel/html.php b/laravel/html.php index 53390187..1007a335 100644 --- a/laravel/html.php +++ b/laravel/html.php @@ -18,14 +18,6 @@ public static function entities($value) /** * Generate a JavaScript reference. * - * - * // Generate a link to a JavaScript file - * echo HTML::script('js/jquery.js'); - * - * // Generate a link to a JavaScript file with attributes - * echo HTML::script('js/jquery.js', array('defer')); - * - * * @param string $url * @param array $attributes * @return string @@ -42,14 +34,6 @@ public static function script($url, $attributes = array()) * * If no media type is selected, "all" will be used. * - * - * // Generate a link to a CSS file - * echo HTML::style('css/common.css'); - * - * // Generate a link to a CSS file with attributes - * echo HTML::style('css/common.css', array('media' => 'print')); - * - * * @param string $url * @param array $attributes * @return string @@ -66,14 +50,6 @@ public static function style($url, $attributes = array()) /** * Generate a HTML span. * - * - * // Generate a HTML span element - * echo HTML::span('This is inside a span element.'); - * - * // Generate a HTML span element with attributes - * echo HTML::span('This is inside a span.', array('class' => 'text')); - * - * * @param string $value * @param array $attributes * @return string @@ -86,14 +62,6 @@ public static function span($value, $attributes = array()) /** * Generate a HTML link. * - * - * // Generate a HTML link element - * echo HTML::link('user/profile', 'User Profile'); - * - * // Generate a HTML link element with attributes - * echo HTML::link('user/profile', 'User Profile', array('class' => 'profile')); - * - * * @param string $url * @param string $title * @param array $attributes @@ -154,15 +122,6 @@ public static function link_to_secure_asset($url, $title, $attributes = array()) * * An array of parameters may be specified to fill in URI segment wildcards. * - * - * // Generate a link to the "profile" route - * echo HTML::link_to_route('profile', 'User Profile'); - * - * // Generate a link to a route that has wildcard segments - * // Example: /user/profile/(:any) - * echo HTML::link_to_route('profile', 'User Profile', array($username)); - * - * * @param string $name * @param string $title * @param array $parameters @@ -193,17 +152,6 @@ public static function link_to_secure_route($name, $title, $parameters = array() * * The E-Mail address will be obfuscated to protect it from spam bots. * - * - * // Generate a HTML mailto link - * echo HTML::mailto('example@gmail.com'); - * - * // Generate a HTML mailto link with a title - * echo HTML::mailto('example@gmail.com', 'E-Mail Me!'); - * - * // Generate a HTML mailto link with attributes - * echo HTML::mailto('example@gmail.com', 'E-Mail Me', array('class' => 'email')); - * - * * @param string $email * @param string $title * @param array $attributes @@ -234,17 +182,6 @@ public static function email($email) /** * Generate an HTML image element. * - * - * // Generate a HTML image element - * echo HTML::image('img/profile.jpg'); - * - * // Generate a HTML image element with Alt text - * echo HTML::image('img/profile.jpg', 'Profile Photo'); - * - * // Generate a HTML image element with attributes - * echo HTML::image('img/profile.jpg', 'Profile Photo', array('class' => 'profile')); - * - * * @param string $url * @param string $alt * @param array $attributes @@ -260,14 +197,6 @@ public static function image($url, $alt = '', $attributes = array()) /** * Generate an ordered list of items. * - * - * // Generate an ordered list of items - * echo HTML::ol(array('Small', 'Medium', 'Large')); - * - * // Generate an ordered list of items with attributes - * echo HTML::ol(array('Small', 'Medium', 'Large'), array('class' => 'sizes')); - * - * * @param array $list * @param array $attributes * @return string @@ -280,14 +209,6 @@ public static function ol($list, $attributes = array()) /** * Generate an un-ordered list of items. * - * - * // Generate an un-ordered list of items - * echo HTML::ul(array('Small', 'Medium', 'Large')); - * - * // Generate an un-ordered list of items with attributes - * echo HTML::ul(array('Small', 'Medium', 'Large'), array('class' => 'sizes')); - * - * * @param array $list * @param array $attributes * @return string @@ -379,20 +300,6 @@ public static function obfuscate($value) * Magic Method for handling dynamic static methods. * * This method primarily handles dynamic calls to create links to named routes. - * - * - * // Create a link to the "profile" named route - * echo HTML::link_to_profile('Profile'); - * - * // Create a link to a named route with URI wildcard parameters - * echo HTML::link_to_posts('Posts', array($year, $month)); - * - * // Create a HTTPS link to the "profile" named route - * echo HTML::link_to_secure_profile('Profile'); - * - * // Create a HTTPS link to a named route URI wildcard parameters - * echo HTML::link_to_secure_posts('Posts', array($year, $month)); - * */ public static function __callStatic($method, $parameters) { diff --git a/laravel/inflector.php b/laravel/inflector.php index 03e30d52..2f7e8eb5 100644 --- a/laravel/inflector.php +++ b/laravel/inflector.php @@ -117,14 +117,6 @@ class Inflector { /** * Get the plural form of a word if the specified count is greater than one. * - * - * // Returns "friend" - * echo Inflector::plural_if('friend', 1); - * - * // Returns "friends" - * echo Inflector::plural_if('friend', 2); - * - * * @param string $value * @param int $count * @return string diff --git a/laravel/input.php b/laravel/input.php index 284c0adb..a73cfafd 100644 --- a/laravel/input.php +++ b/laravel/input.php @@ -7,7 +7,34 @@ class Input { * * @var array */ - public static $input; + protected $input; + + /** + * The $_FILES array for the current request. + * + * @var array + */ + protected $files; + + /** + * The key used to store old input in the session. + * + * @var string + */ + const old_input = 'laravel_old_input'; + + /** + * Create a new input manager instance. + * + * @param array $input + * @param array $files + * @return void + */ + public function __construct($input, $files) + { + $this->input = $input; + $this->files = $files; + } /** * Get all of the input data for the request. @@ -16,9 +43,9 @@ class Input { * * @return array */ - public static function all() + public function all() { - return array_merge(static::get(), static::file()); + return array_merge($this->get(), $this->file()); } /** @@ -27,9 +54,9 @@ public static function all() * @param string $key * @return bool */ - public static function has($key) + public function has($key) { - return ( ! is_null(static::get($key)) and trim((string) static::get($key)) !== ''); + return ( ! is_null($this->get($key)) and trim((string) $this->get($key)) !== ''); } /** @@ -37,21 +64,13 @@ public static function has($key) * * This method should be used for all request methods (GET, POST, PUT, and DELETE). * - * - * // Get an item from the input to the application - * $value = Input::get('name'); - * - * // Get an item from the input and return "Fred" if the item doesn't exist - * $value = Input::get('name', 'Fred'); - * - * * @param string $key * @param mixed $default * @return mixed */ - public static function get($key = null, $default = null) + public function get($key = null, $default = null) { - return Arr::get(static::$input, $key, $default); + return Arr::get($this->input, $key, $default); } /** @@ -60,27 +79,19 @@ public static function get($key = null, $default = null) * @param string $key * @return bool */ - public static function had($key) + public function had($key) { - return ( ! is_null(static::old($key)) and trim((string) static::old($key)) !== ''); + return ( ! is_null($this->old($key)) and trim((string) $this->old($key)) !== ''); } /** * Get input data from the previous request. * - * - * // Get an item from the previous request's input - * $value = Input::old('name'); - * - * // Get an item from the previous request's input and return "Fred" if it doesn't exist. - * $value = Input::old('name', 'Fred'); - * - * * @param string $key * @param mixed $default * @return string */ - public static function old($key = null, $default = null) + public function old($key = null, $default = null) { if (Config::get('session.driver') == '') { @@ -89,29 +100,19 @@ public static function old($key = null, $default = null) $driver = IoC::container()->resolve('laravel.session'); - return Arr::get($driver->get('laravel_old_input', array()), $key, $default); + return Arr::get($driver->get(Input::old_input, array()), $key, $default); } /** * Get an item from the uploaded file data. * - * "Dot" syntax may be used to get a specific item from the file array. - * - * - * // Get the array of information regarding an uploaded file - * $file = Input::file('picture'); - * - * // Get an element from the array of information regarding an uploaded file - * $size = Input::file('picture.size'); - * - * * @param string $key * @param mixed $default * @return array */ - public static function file($key = null, $default = null) + public function file($key = null, $default = null) { - return Arr::get($_FILES, $key, $default); + return Arr::get($this->files, $key, $default); } /** @@ -119,49 +120,13 @@ public static function file($key = null, $default = null) * * This method is simply a convenient wrapper around move_uploaded_file. * - * - * // Move the "picture" file to a permament location on disk - * Input::upload('picture', PUBLIC_PATH.'img/picture.jpg'); - * - * * @param string $key * @param string $path * @return bool */ - public static function upload($key, $path) + public function upload($key, $path) { - return array_key_exists($key, $_FILES) ? File::upload($key, $path, $_FILES) : false; + return array_key_exists($key, $this->files) ? File::upload($key, $path, $this->files) : false; } -} - -/** - * Set the input values for the current request. - */ -$input = array(); - -switch (Request::method()) -{ - case 'GET': - $input = $_GET; - break; - - case 'POST': - $input = $_POST; - break; - - case 'PUT': - case 'DELETE': - if (Request::spoofed()) - { - $input = $_POST; - } - else - { - parse_str(file_get_contents('php://input'), $input); - } -} - -unset($input[Request::spoofer]); - -Input::$input = $input; \ No newline at end of file +} \ No newline at end of file diff --git a/laravel/lang.php b/laravel/lang.php index 3cbfe15a..a9ee2021 100644 --- a/laravel/lang.php +++ b/laravel/lang.php @@ -45,11 +45,13 @@ class Lang { * @param string $key * @param array $replacements * @param string $language + * @param array $paths * @return void */ - protected function __construct($key, $replacements = array(), $language = null) + protected function __construct($key, $replacements = array(), $language = null, $paths = array()) { $this->key = $key; + $this->paths = $paths; $this->language = $language; $this->replacements = $replacements; } @@ -60,29 +62,19 @@ protected function __construct($key, $replacements = array(), $language = null) * @param string $key * @param array $replacements * @param string $language + * @param array $paths * @return Lang */ - public static function line($key, $replacements = array(), $language = null) + public static function line($key, $replacements = array(), $language = null, $paths = array()) { - return new static($key, $replacements, $language); + if (count($paths) == 0) $paths = array(SYS_LANG_PATH, LANG_PATH); + + return new static($key, $replacements, $language, $paths); } /** * Get the language line. * - * A default value may also be specified, which will be returned in the language line doesn't exist. - * - * - * // Retrieve a language line in the default language - * echo Lang::line('validation.required')->get(); - * - * // Retrieve a language line for a given language - * echo Lang::line('validation.required')->get('sp'); - * - * // Retrieve a language line and return "Fred" if it doesn't exist - * echo Lang::line('validation.required')->get('en', 'Fred'); - * - * * @param string $language * @param string $default * @return string @@ -111,10 +103,6 @@ public function get($language = null, $default = null) /** * Parse a language key. * - * Language keys follow a {file}.{key} convention. If a specific language key is not - * specified, an exception will be thrown. Setting entire language files at run-time - * is not currently supported. - * * @param string $key * @return array */ @@ -131,8 +119,6 @@ protected function parse($key) /** * Load a language file. * - * If the language file has already been loaded, it will not be loaded again. - * * @param string $file * @return bool */ @@ -142,7 +128,7 @@ protected function load($file) $language = array(); - foreach (array(SYS_LANG_PATH, LANG_PATH) as $directory) + foreach ($this->paths as $directory) { if (file_exists($path = $directory.$this->language.'/'.$file.EXT)) { @@ -157,15 +143,6 @@ protected function load($file) /** * Get the string content of the language line. - * - * This provides a convenient mechanism for displaying language line in views without - * using the "get" method on the language instance. - * - * - * // Display a language line by casting it to a string - * echo Lang::line('messages.welcome'); - * - * */ public function __toString() { diff --git a/laravel/laravel.php b/laravel/laravel.php index efaa47c6..d8d0732b 100644 --- a/laravel/laravel.php +++ b/laravel/laravel.php @@ -3,39 +3,12 @@ // -------------------------------------------------------------- // Bootstrap the core framework components. // -------------------------------------------------------------- -require 'core.php'; +require 'bootstrap/core.php'; // -------------------------------------------------------------- -// Get an instance of the configuration manager. +// Register the framework error handlers. // -------------------------------------------------------------- -set_exception_handler(function($e) -{ - call_user_func(Config::get('error.handler'), $e); -}); - -set_error_handler(function($number, $error, $file, $line) -{ - $exception = new \ErrorException($error, $number, 0, $file, $line); - - call_user_func(Config::get('error.handler'), $exception); -}); - -register_shutdown_function(function() -{ - if ( ! is_null($error = error_get_last())) - { - $exception = new \ErrorException($error['message'], $error['type'], 0, $error['file'], $error['line']); - - call_user_func(Config::get('error.handler'), $exception); - } -}); - -// -------------------------------------------------------------- -// Set the error reporting and display levels. -// -------------------------------------------------------------- -error_reporting(-1); - -ini_set('display_errors', 'Off'); +require SYS_PATH.'bootstrap/errors'.EXT; // -------------------------------------------------------------- // Set the default timezone. @@ -55,7 +28,11 @@ // -------------------------------------------------------------- // Route the request and get the response from the route. // -------------------------------------------------------------- -$route = $container->resolve('laravel.routing.router')->route(Request::method(), Request::uri()); +$request = $container->resolve('laravel.request'); + +list($method, $uri) = array($request->method(), $request->uri()); + +$route = $container->resolve('laravel.routing.router')->route($request, $method, $uri); if ( ! is_null($route)) { @@ -76,7 +53,9 @@ // -------------------------------------------------------------- if (isset($session)) { - $session->close($container->resolve('laravel.session'), Config::get('session')); + $flash = array(Input::old_input => $container->resolve('laravel.input')->get()); + + $session->close($container->resolve('laravel.session'), Config::get('session'), $flash); } // -------------------------------------------------------------- diff --git a/laravel/loader.php b/laravel/loader.php index 6d61fea8..f76d8ed6 100644 --- a/laravel/loader.php +++ b/laravel/loader.php @@ -48,11 +48,6 @@ public static function load($class) * * Note: Aliases are lazy-loaded, so the aliased class will not be included until it is needed. * - * - * // Register an alias for the "SwiftMailer\Transport" class - * Loader::alias('Transport', 'SwiftMailer\\Transport'); - * - * * @param string $alias * @param string $class * @return void @@ -65,13 +60,6 @@ public static function alias($alias, $class) /** * Register a path with the auto-loader. * - * The registered path will be searched when auto-loading classes. - * - * - * // Register a path to be searched by the auto-loader - * Loader::path('path/to/files'); - * - * * @param string $path * @return void */ @@ -83,11 +71,6 @@ public static function path($path) /** * Remove an alias from the auto-loader's alias registrations. * - * - * // Remove the "Transport" alias from the registered aliases - * Loader::forget_alias('Transport'); - * - * * @param string $alias * @return void */ diff --git a/laravel/redirect.php b/laravel/redirect.php index e9025f1b..06d38c8a 100644 --- a/laravel/redirect.php +++ b/laravel/redirect.php @@ -5,14 +5,6 @@ class Redirect extends Response { /** * Create a redirect response. * - * - * // Create a redirect response to a given URL - * return Redirect::to('user/profile'); - * - * // Create a redirect with a given status code - * return Redirect::to('user/profile', 301); - * - * * @param string $url * @param int $status * @param bool $https @@ -28,11 +20,6 @@ public static function to($url, $status = 302, $https = false) /** * Create a redirect response to a HTTPS URL. * - * - * // Create a redirect response to a HTTPS URL - * return Redirect::to_secure('user/profile'); - * - * * @param string $url * @param int $status * @return Response @@ -47,11 +34,6 @@ public static function to_secure($url, $status = 302) * * This is useful for passing status messages or other temporary data to the next request. * - * - * // Create a redirect and flash a messages to the session - * return Redirect::to_profile()->with('message', 'Welcome Back!'); - * - * * @param string $key * @param mixed $value * @return Response @@ -70,17 +52,6 @@ public function with($key, $value) /** * Magic Method to handle creation of redirects to named routes. - * - * - * // Create a redirect to the "profile" route - * return Redirect::to_profile(); - * - * // Create a redirect to the "profile" route with wildcard segments - * return Redirect::to_profile(array($username)); - * - * // Create a redirect to the "profile" route using HTTPS - * return Redirect::to_secure_profile(); - * */ public static function __callStatic($method, $parameters) { diff --git a/laravel/request.php b/laravel/request.php index 70c098dd..417257fa 100644 --- a/laravel/request.php +++ b/laravel/request.php @@ -7,15 +7,44 @@ class Request { * * @var Routing\Route */ - public static $route; + public $route; /** - * The request data key that is used to indicate the spoofed request method. + * The $_SERVER array for the current request. + * + * @var array + */ + protected $server; + + /** + * The $_POST array for the current request. + * + * @var array + */ + protected $post; + + /** + * The request data key that is used to indicate a spoofed request method. * * @var string */ const spoofer = '__spoofer'; + /** + * Create a new request instance. + * + * @param URI $uri + * @param array $server + * @param array $post + * @return void + */ + public function __construct(URI $uri, $server, $post) + { + $this->uri = $uri; + $this->post = $post; + $this->server = $server; + } + /** * Get the URI for the current request. * @@ -23,9 +52,9 @@ class Request { * * @return string */ - public static function uri() + public function uri() { - return URI::get(); + return $this->uri->get(); } /** @@ -33,19 +62,11 @@ public static function uri() * * The format is determined by essentially taking the "extension" of the URI. * - * - * // Returns "html" for a request to "/user/profile" - * $format = Request::format(); - * - * // Returns "json" for a request to "/user/profile.json" - * $format = Request::format(); - * - * * @return string */ - public static function format() + public function format() { - return (($extension = pathinfo(URI::get(), PATHINFO_EXTENSION)) !== '') ? $extension : 'html'; + return (($extension = pathinfo($this->uri->get(), PATHINFO_EXTENSION)) !== '') ? $extension : 'html'; } /** @@ -57,9 +78,9 @@ public static function format() * * @return string */ - public static function method() + public function method() { - return (static::spoofed()) ? $_POST[Request::spoofer] : $_SERVER['REQUEST_METHOD']; + return ($this->spoofed()) ? $this->post[Request::spoofer] : $this->server['REQUEST_METHOD']; } /** @@ -67,21 +88,13 @@ public static function method() * * Like most array retrieval methods, a default value may be specified. * - * - * // Get an item from the $_SERVER array - * $value = Request::server('http_x_requested_for'); - * - * // Get an item from the $_SERVER array or return a default value - * $value = Request::server('http_x_requested_for', '127.0.0.1'); - * - * * @param string $key * @param mixed $default * @return string */ - public static function server($key = null, $default = null) + public function server($key = null, $default = null) { - return Arr::get($_SERVER, strtoupper($key), $default); + return Arr::get($this->server, strtoupper($key), $default); } /** @@ -93,28 +106,18 @@ public static function server($key = null, $default = null) * * @return bool */ - public static function spoofed() + public function spoofed() { - return is_array($_POST) and array_key_exists(Request::spoofer, $_POST); + return is_array($this->post) and array_key_exists(Request::spoofer, $this->post); } /** * Get the requestor's IP address. * - * A default may be passed and will be returned in the event the IP can't be determined - * - * - * // Get the requestor's IP address - * $ip = Request::ip(); - * - * // Get the requestor's IP address or return a default value - * $ip = Request::ip('127.0.0.1'); - * - * * @param mixed $default * @return string */ - public static function ip($default = '0.0.0.0') + public function ip($default = '0.0.0.0') { if (isset($_SERVER['HTTP_X_FORWARDED_FOR'])) { @@ -140,9 +143,9 @@ public static function ip($default = '0.0.0.0') * * @return string */ - public static function protocol() + public function protocol() { - return (isset($_SERVER['HTTPS']) and $_SERVER['HTTPS'] !== 'off') ? 'https' : 'http'; + return (isset($this->server['HTTPS']) and $this->server['HTTPS'] !== 'off') ? 'https' : 'http'; } /** @@ -150,9 +153,9 @@ public static function protocol() * * @return bool */ - public static function secure() + public function secure() { - return static::protocol() == 'https'; + return $this->protocol() == 'https'; } /** @@ -160,11 +163,11 @@ public static function secure() * * @return bool */ - public static function ajax() + public function ajax() { - if ( ! isset($_SERVER['HTTP_X_REQUESTED_WITH'])) return false; + if ( ! isset($this->server['HTTP_X_REQUESTED_WITH'])) return false; - return strtolower($_SERVER['HTTP_X_REQUESTED_WITH']) === 'xmlhttprequest'; + return strtolower($this->server['HTTP_X_REQUESTED_WITH']) === 'xmlhttprequest'; } /** @@ -172,6 +175,6 @@ public static function ajax() * * @return Route */ - public function route() { return static::$route; } + public function route() { return $this->route; } } \ No newline at end of file diff --git a/laravel/response.php b/laravel/response.php index 0ead4c6b..c1533e18 100644 --- a/laravel/response.php +++ b/laravel/response.php @@ -95,14 +95,6 @@ public function __construct($content, $status = 200, $headers = array()) /** * Create a new response instance. * - * - * // Create a response instance - * return Response::make('Hello World'); - * - * // Create a response instance with a given status code - * return Response::make('Hello World', 200); - * - * * @param mixed $content * @param int $status * @param array $headers @@ -116,14 +108,6 @@ public static function make($content, $status = 200, $headers = array()) /** * Create a new response instance containing a view. * - * - * // Create a new response instance with view content - * return Response::view('home.index'); - * - * // Create a new response instance with a view and bound data - * return Response::view('home.index', array('name' => 'Fred')); - * - * * @param string $view * @param array $data * @return Response @@ -136,14 +120,6 @@ public static function view($view, $data = array()) /** * Create a new response instance containing a named view. * - * - * // Create a new response instance with a named view - * return Response::with('layout'); - * - * // Create a new response instance with a named view and bound data - * return Response::with('layout', array('name' => 'Fred')); - * - * * @param string $name * @param array $data * @return Response @@ -160,11 +136,6 @@ public static function with($name, $data = array()) * * Note: The specified error code should correspond to a view in your views/error directory. * - * - * // Create an error response for status 500 - * return Response::error('500'); - * - * * @param int $code * @param array $data * @return Response @@ -272,14 +243,6 @@ public function status($status) /** * Magic Method for handling the dynamic creation of Responses containing named views. - * - * - * // Create a Response instance with the "layout" named view - * $response = Response::with_layout(); - * - * // Create a Response instance with the "layout" named view and bound data - * $response = Response::with_layout(array('name' => 'Fred')); - * */ public static function __callStatic($method, $parameters) { diff --git a/laravel/routing/loader.php b/laravel/routing/loader.php index d52f760c..4c699fbc 100644 --- a/laravel/routing/loader.php +++ b/laravel/routing/loader.php @@ -43,9 +43,6 @@ public function __construct($base, $nest) /** * Load the applicable routes for a given URI. * - * The application route directory will be checked for nested route files and an - * array of all applicable routes will be returned based on the URI segments. - * * @param string $uri * @return array */ @@ -80,9 +77,6 @@ protected function nested($segments) /** * Get every route defined for the application. * - * For fast performance, if the routes have already been loaded once, they will not - * be loaded again, and the same routes will be returned on subsequent calls. - * * @return array */ public function everything() diff --git a/laravel/routing/router.php b/laravel/routing/router.php index 40cd2095..5951465c 100644 --- a/laravel/routing/router.php +++ b/laravel/routing/router.php @@ -67,13 +67,12 @@ public function find($name) /** * Search the routes for the route matching a request method and URI. * - * If no route can be found, the application controllers will be searched. - * - * @param string $method - * @param string $uri + * @param Request $request + * @param string $method + * @param string $uri * @return Route */ - public function route($method, $uri) + public function route(Request $request, $method, $uri) { $routes = $this->loader->load($uri); @@ -85,7 +84,7 @@ public function route($method, $uri) // no need to spin through all of the routes. if (isset($routes[$destination])) { - return Request::$route = new Route($destination, $routes[$destination], array()); + return $request->route = new Route($destination, $routes[$destination], array()); } foreach ($routes as $keys => $callback) @@ -101,20 +100,18 @@ public function route($method, $uri) if (preg_match('#^'.$this->translate_wildcards($key).'$#', $destination)) { - return Request::$route = new Route($keys, $callback, $this->parameters($destination, $key)); + return $request->route = new Route($keys, $callback, $this->parameters($destination, $key)); } } } } - return Request::$route = $this->route_to_controller($method, $uri, $destination); + return $request->route = $this->route_to_controller($method, $uri, $destination); } /** * Attempt to find a controller for the incoming request. * - * If no corresponding controller can be found, NULL will be returned. - * * @param string $method * @param string $uri * @param string $destination diff --git a/laravel/security/auth.php b/laravel/security/auth.php index b0e684dd..333400ba 100644 --- a/laravel/security/auth.php +++ b/laravel/security/auth.php @@ -19,6 +19,13 @@ class Auth { */ protected $session; + /** + * The key used when storing the user ID in the session. + * + * @var string + */ + const user_key = 'laravel_user_id'; + /** * Create a new authenticator instance. * @@ -51,7 +58,7 @@ public function user() { if ( ! is_null($this->user)) return $this->user; - return $this->user = call_user_func(Config::get('auth.user'), $this->session->get('laravel_user_id')); + return $this->user = call_user_func(Config::get('auth.user'), $this->session->get(Auth::user_key)); } /** @@ -88,7 +95,7 @@ public function remember($user) { $this->user = $user; - $this->session->put('laravel_user_id', $user->id); + $this->session->put(Auth::user_key, $user->id); } /** @@ -102,7 +109,7 @@ public function logout() $this->user = null; - $this->session->forget('laravel_user_id'); + $this->session->forget(Auth::user_key); } } \ No newline at end of file diff --git a/laravel/session/drivers/cookie.php b/laravel/session/drivers/cookie.php index 9261773c..36782217 100644 --- a/laravel/session/drivers/cookie.php +++ b/laravel/session/drivers/cookie.php @@ -1,6 +1,5 @@ crypter = $crypter; + $this->cookies = $cookies; } /** @@ -37,9 +45,9 @@ public function __construct(Crypter $crypter) */ public function load($id) { - if (C::has('session_payload')) + if ($this->cookies->has('session_payload')) { - return unserialize($this->crypter->decrypt(C::get('session_payload'))); + return unserialize($this->crypter->decrypt($this->cookies->get('session_payload'))); } } @@ -56,7 +64,7 @@ public function save($session, $config) $payload = $this->crypter->encrypt(serialize($session)); - C::put('session_payload', $payload, $lifetime, $path, $domain); + $this->cookies->put('session_payload', $payload, $lifetime, $path, $domain); } /** @@ -67,7 +75,7 @@ public function save($session, $config) */ public function delete($id) { - C::forget('session_payload'); + $this->cookies->forget('session_payload'); } } \ No newline at end of file diff --git a/laravel/session/manager.php b/laravel/session/manager.php index 5b78f22b..0516184e 100644 --- a/laravel/session/manager.php +++ b/laravel/session/manager.php @@ -91,10 +91,16 @@ private function expired($session, $config) * * @param Payload $payload * @param array $config + * @param array $flash * @return void */ - public function close(Payload $payload, $config) + public function close(Payload $payload, $config, $flash = array()) { + foreach ($flash as $key => $value) + { + $this->driver->flash($key, $value); + } + $this->driver->save($payload->age(), $config); $this->transporter->put($payload->session['id'], $config); diff --git a/laravel/session/transporters/cookie.php b/laravel/session/transporters/cookie.php index b1d5c9ad..82fe14cb 100644 --- a/laravel/session/transporters/cookie.php +++ b/laravel/session/transporters/cookie.php @@ -1,9 +1,25 @@ cookies = $cookies; + } + /** * Get the session identifier for the request. * @@ -12,7 +28,7 @@ class Cookie implements Transporter { */ public function get($config) { - return C::get('laravel_session'); + return $this->cookies->get('laravel_session'); } /** @@ -26,7 +42,7 @@ public function put($id, $config) { $minutes = ($config['expire_on_close']) ? 0 : $config['lifetime']; - C::put('laravel_session', $id, $minutes, $config['path'], $config['domain']); + $this->cookies->put('laravel_session', $id, $minutes, $config['path'], $config['domain']); } } \ No newline at end of file diff --git a/laravel/uri.php b/laravel/uri.php index 59db01e0..9e2ab73c 100644 --- a/laravel/uri.php +++ b/laravel/uri.php @@ -9,7 +9,25 @@ class URI { * * @var string */ - protected static $uri; + protected $uri; + + /** + * The $_SERVER array for the current request. + * + * @var array + */ + protected $server; + + /** + * Create a new URI parser instance. + * + * @param array $server + * @return void + */ + public function __construct($server) + { + $this->server = $server; + } /** * Determine the request URI. @@ -23,39 +41,28 @@ class URI { * * @return string */ - public static function get() + public function get() { - if ( ! is_null(static::$uri)) return static::$uri; + if ( ! is_null($this->uri)) return $this->uri; - if (($uri = static::from_server()) === false) + if (($uri = $this->from_server()) === false) { throw new \Exception('Malformed request URI. Request terminated.'); } - return static::$uri = static::format(static::clean($uri)); + return $this->uri = $this->format($this->clean($uri)); } /** * Get a given URI segment from the URI for the current request. * - * - * // Get the first segment from the request URI - * $first = Request::uri()->segment(1); - * - * // Get the second segment or return a default value if it doesn't exist - * $second = Request::uri()->segment(2, 'Taylor'); - * - * // Get all of the segments for the request URI - * $segments = Request::uri()->segment(); - * - * * @param int $segment * @param mixed $default * @return string */ - public static function segment($segment = null, $default = null) + public function segment($segment = null, $default = null) { - $segments = Arr::without(explode('/', static::get()), array('')); + $segments = Arr::without(explode('/', $this->get()), array('')); if ( ! is_null($segment)) $segment = $segment - 1; @@ -67,20 +74,20 @@ public static function segment($segment = null, $default = null) * * @return string */ - protected static function from_server() + protected function from_server() { // If the PATH_INFO $_SERVER element is set, we will use since it contains // the request URI formatted perfectly for Laravel's routing engine. - if (isset($_SERVER['PATH_INFO'])) + if (isset($this->server['PATH_INFO'])) { - return $_SERVER['PATH_INFO']; + return $this->server['PATH_INFO']; } // If the REQUEST_URI is set, we need to extract the URL path since this // should return the URI formatted in a manner similar to PATH_INFO. - elseif (isset($_SERVER['REQUEST_URI'])) + elseif (isset($this->server['REQUEST_URI'])) { - return parse_url($_SERVER['REQUEST_URI'], PHP_URL_PATH); + return parse_url($this->server['REQUEST_URI'], PHP_URL_PATH); } throw new \Exception('Unable to determine the request URI.'); @@ -95,7 +102,7 @@ protected static function from_server() * @param string $uri * @return string */ - protected static function clean($uri) + protected function clean($uri) { foreach (array(parse_url(Config::get('application.url'), PHP_URL_PATH), '/index.php') as $value) { @@ -113,7 +120,7 @@ protected static function clean($uri) * @param string $uri * @return string */ - protected static function format($uri) + protected function format($uri) { return (($uri = trim($uri, '/')) == '') ? '/' : $uri; } diff --git a/laravel/url.php b/laravel/url.php index 36ce21bf..8edec1b5 100644 --- a/laravel/url.php +++ b/laravel/url.php @@ -7,14 +7,6 @@ class URL { * * If the given URL is already well-formed, it will be returned unchanged. * - * - * // Generate an application URL from a given URI - * echo URL::to('user/profile'); - * - * // Generate an application URL with HTTPS - * echo URL::to('user/profile', true); - * - * * @param string $url * @param bool $https * @return string @@ -33,11 +25,6 @@ public static function to($url = '', $https = false) /** * Generate an application URL with HTTPS. * - * - * // Generate an application URL with HTTPS - * echo URL::to_secure('user/profile'); - * - * * @param string $url * @return string */ @@ -52,21 +39,13 @@ public static function to_secure($url = '') * The index file will not be added to asset URLs. If the HTTPS option is not * specified, HTTPS will be used when the active request is also using HTTPS. * - * - * // Generate a URL to an asset - * echo URL::to_asset('img/picture.jpg'); - * - * // Generate a URL to a an asset with HTTPS - * echo URL::to_asset('img/picture.jpg', true); - * - * * @param string $url * @param bool $https * @return string */ public static function to_asset($url, $https = null) { - if (is_null($https)) $https = Request::secure(); + if (is_null($https)) $https = IoC::container()->resolve('laravel.request')->secure(); return str_replace('index.php/', '', static::to($url, $https)); } @@ -78,16 +57,6 @@ public static function to_asset($url, $https = null) * parameter to the method. The values of this array will be used to fill the * wildcard segments of the route URI. * - * Optional parameters will be convereted to spaces if no parameter values are specified. - * - * - * // Generate the URL for a given route - * echo URL::to_route('profile'); - * - * // Generate the URL for a given route with wildcard segments - * echo URL::to_route('profile', array($username)); - * - * * @param string $name * @param array $parameters * @param bool $https @@ -119,14 +88,6 @@ public static function to_route($name, $parameters = array(), $https = false) /** * Generate a HTTPS URL from a route name. * - * - * // Generate the URL for a route with HTTPS - * echo URL::to_secure_route('profile'); - * - * // Generate the URL for a route with HTTPS and wildcard segments - * echo URL::to_secure_route('profile', array($username)); - * - * * @param string $name * @param array $parameters * @return string @@ -158,17 +119,6 @@ public static function slug($title, $separator = '-') /** * Magic Method for dynamically creating URLs to named routes. - * - * - * // Generate the URL for the "profile" named route - * echo URL::to_profile(); - * - * // Generate the URL for the "profile" named route with wildcard segments - * echo URL::to_profile(array($username)); - * - * // Generate the URL for the "profile" named route with HTTPS - * echo URL::to_secure_profile(); - * */ public static function __callStatic($method, $parameters) { diff --git a/laravel/validation/messages.php b/laravel/validation/messages.php index 26985cc8..3c3f2689 100644 --- a/laravel/validation/messages.php +++ b/laravel/validation/messages.php @@ -26,11 +26,6 @@ public function __construct($messages = array()) * * Duplicate messages will not be added. * - * - * // Add a message to the message collector - * $messages->add('email', 'The e-mail address is invalid.'); - * - * * @param string $key * @param string $message * @return void @@ -57,16 +52,6 @@ public function has($key) /** * Get the first message for a given key. * - * Optionally, a format may be specified for the returned message. - * - * - * // Get the first message for the e-mail attribute - * echo $messages->first('email'); - * - * // Get the first message for the e-mail attribute using a format - * echo $messages->first('email', '

:message

'); - *
- * * @param string $key * @param string $format * @return string @@ -79,16 +64,6 @@ public function first($key, $format = ':message') /** * Get all of the messages for a key. * - * Optionally, a format may be specified for the returned messages. - * - * - * // Get all of the messages for the e-mail attribute - * $messages = $messages->get('email'); - * - * // Get all of the messages for the e-mail attribute using a format - * $messages = $messages->get('email', '

:message

'); - *
- * * @param string $key * @param string $format * @return array @@ -103,11 +78,6 @@ public function get($key = null, $format = ':message') /** * Get all of the messages for every key. * - * - * // Get all of the error messages using a format - * $messages = $messages->all('

:message

'); - *
- * * @param string $format * @return array */ diff --git a/laravel/validation/validator.php b/laravel/validation/validator.php index 74f23de1..b17cd814 100644 --- a/laravel/validation/validator.php +++ b/laravel/validation/validator.php @@ -457,7 +457,7 @@ protected function get_message($attribute, $rule) // the default error message for the appropriate units. if (in_array($rule, $this->size_rules) and ! $this->has_rule($attribute, $this->numeric_rules)) { - return (array_key_exists($attribute, Input::files())) + return (array_key_exists($attribute, IoC::container()->resolve('laravel.input')->files())) ? rtrim($message, '.').' '.Lang::line('validation.kilobytes')->get($this->language).'.' : rtrim($message, '.').' '.Lang::line('validation.characters')->get($this->language).'.'; } diff --git a/laravel/view.php b/laravel/view.php index 752c7ce6..00355481 100644 --- a/laravel/view.php +++ b/laravel/view.php @@ -1,5 +1,161 @@ path = $path; + $this->composer = $composer; + } + + /** + * Create a new view instance. + * + * The name of the view given to this method should correspond to a view + * within your application views directory. Dots or slashes may used to + * reference views within sub-directories. + * + * @param string $view + * @param array $data + * @return View + */ + public function make($view, $data = array()) + { + return new View($this, $this->composer, $view, $data, $this->path($view)); + } + + /** + * Create a new view instance from a view name. + * + * View names are defined in the application composers file. + * + * @param string $name + * @param array $data + * @return View + */ + protected function of($name, $data = array()) + { + if ( ! is_null($view = $this->composer->name($name))) + { + return $this->make($view, $data); + } + + throw new \Exception("Named view [$name] is not defined."); + } + + /** + * Get the path to a given view on disk. + * + * @param string $view + * @return string + */ + protected function path($view) + { + $view = str_replace('.', '/', $view); + + if (file_exists($path = $this->path.$view.BLADE_EXT)) + { + return $path; + } + elseif (file_exists($path = $this->path.$view.EXT)) + { + return $path; + } + + throw new \Exception('View ['.$view.'] does not exist.'); + } + + /** + * Magic Method for handling the dynamic creation of named views. + */ + public function __call($method, $parameters) + { + if (strpos($method, 'of_') === 0) + { + return $this->of(substr($method, 3), Arr::get($parameters, 0, array())); + } + } + +} + + +class View_Composer { + + /** + * The view composers. + * + * @var array + */ + protected $composers; + + /** + * Create a new view composer instance. + * + * @param array $composers + * @return void + */ + public function __construct($composers) + { + $this->composers = $composers; + } + + /** + * Find the key for a view by name. + * + * @param string $name + * @return string + */ + public function name($name) + { + foreach ($this->composers as $key => $value) + { + if ($name === $value or (isset($value['name']) and $name === $value['name'])) { return $key; } + } + } + + /** + * Call the composer for the view instance. + * + * @param View $view + * @return void + */ + public function compose(View $view) + { + if (isset($this->composers['shared'])) call_user_func($this->composers['shared'], $view); + + if (isset($this->composers[$view->view])) + { + foreach ((array) $this->composers[$view->view] as $key => $value) + { + if ($value instanceof \Closure) return call_user_func($value, $view); + } + } + } + +} + + class View { /** @@ -23,30 +179,53 @@ class View { */ protected $path; + /** + * The view composer instance. + * + * @var View_Composer + */ + protected $composer; + + /** + * The view factory instance, which is used to create sub-views. + * + * @var View_Factory + */ + protected $factory; + /** * Create a new view instance. * - * @param string $view - * @param array $data + * @param View_Factory $factory + * @param View_Composer $composer + * @param string $view + * @param array $data + * @param string $path * @return void */ - protected function __construct($view, $data = array()) + public function __construct(View_Factory $factory, View_Composer $composer, $view, $data, $path) { $this->view = $view; $this->data = $data; - $this->path = $this->path($view); + $this->path = $path; + $this->factory = $factory; + $this->composer = $composer; } /** * Create a new view instance. * - * @param string $view - * @param array $data + * The name of the view given to this method should correspond to a view + * within your application views directory. Dots or slashes may used to + * reference views within sub-directories. + * + * @param string $view + * @param array $data * @return View */ public static function make($view, $data = array()) { - return new static($view, $data); + return IoC::container()->resolve('laravel.view')->make($view, $data); } /** @@ -54,48 +233,13 @@ public static function make($view, $data = array()) * * View names are defined in the application composers file. * - * - * // Create a new named view instance - * $view = View::of('layout'); - * - * // Create a new named view instance with bound data - * $view = View::of('layout', array('name' => 'Fred')); - * - * * @param string $name * @param array $data * @return View */ - public static function of($name, $data = array()) + protected function of($name, $data = array()) { - if ( ! is_null($view = Composer::name($name))) - { - return new static($view, $data); - } - - throw new \Exception("Named view [$name] is not defined."); - } - - /** - * Get the path to a given view on disk. - * - * @param string $view - * @return string - */ - protected function path($view) - { - $view = str_replace('.', '/', $view); - - if (file_exists($path = VIEW_PATH.$view.'.blade'.EXT)) - { - return $path; - } - elseif (file_exists($path = VIEW_PATH.$view.EXT)) - { - return $path; - } - - throw new \Exception('View ['.$view.'] does not exist.'); + return IoC::container()->resolve('laravel.view')->of($name, $data); } /** @@ -108,7 +252,7 @@ protected function path($view) */ public function render() { - Composer::compose($this); + $this->composer->compose($this); foreach ($this->data as &$data) { @@ -117,9 +261,9 @@ public function render() ob_start() and extract($this->data, EXTR_SKIP); - $content = ($this->bladed()) ? Blade::parse($this->path) : file_get_contents($this->path); + $file = ($this->bladed()) ? $this->compile() : $this->path; - eval('?>'.$content); + try { include $file; } catch (Exception $e) { ob_get_clean(); throw $e; } return ob_get_clean(); } @@ -134,17 +278,30 @@ protected function bladed() return (strpos($this->path, '.blade'.EXT) !== false); } + /** + * Compile the Bladed view and return the path to the compiled view. + * + * If view will only be re-compiled if the view has been modified since the last compiled + * version of the view was created or no compiled view exists. Otherwise, the path will + * be returned without re-compiling. + * + * @return string + */ + protected function compile() + { + $compiled = $this->factory->path.'compiled/'.md5($this->view); + + if ((file_exists($compiled) and filemtime($this->path) > filemtime($compiled)) or ! file_exists($compiled)) + { + file_put_contents($compiled, Blade::parse($this->path)); + } + + return $path; + } + /** * Add a view instance to the view data. * - * - * // Bind a partial view to the view data - * $view->partial('footer', 'partials/footer'); - * - * // Bind a partial view to the view data with it's own bound data - * $view->partial('footer', 'partials/footer', array('name' => 'Fred')); - * - * * @param string $key * @param string $view * @param array $data @@ -152,7 +309,7 @@ protected function bladed() */ public function partial($key, $view, $data = array()) { - return $this->with($key, new static($view, $data)); + return $this->with($key, $this->factory->make($view, $data)); } /** @@ -160,11 +317,6 @@ public function partial($key, $view, $data = array()) * * Bound data will be available to the view as variables. * - * - * // Bind a piece of data to a view instance - * $view->with('name', 'Fred'); - * - * * @param string $key * @param mixed $value * @return View @@ -172,6 +324,7 @@ public function partial($key, $view, $data = array()) public function with($key, $value) { $this->data[$key] = $value; + return $this; } @@ -207,76 +360,4 @@ public function __unset($key) unset($this->data[$key]); } - /** - * Magic Method for handling the dynamic creation of named views. - * - * - * // Create an instance of the "layout" named view - * $view = View::of_layout(); - * - * // Create an instance of the "layout" named view with bound data - * $view = View::of_layout(array('name' => 'Fred')); - * - */ - public static function __callStatic($method, $parameters) - { - if (strpos($method, 'of_') === 0) - { - return static::of(substr($method, 3), Arr::get($parameters, 0, array())); - } - } - -} - -/** - * The view composer class is responsible for calling the composer on a view and - * searching through the view composers for a given view name. - */ -class Composer { - - /** - * The view composers. - * - * @var array - */ - public static $composers; - - /** - * Find the key for a view by name. - * - * @param string $name - * @return string - */ - public static function name($name) - { - foreach (static::$composers as $key => $value) - { - if ($name === $value or (isset($value['name']) and $name === $value['name'])) { return $key; } - } - } - - /** - * Call the composer for the view instance. - * - * @param View $view - * @return void - */ - public static function compose(View $view) - { - if (isset(static::$composers['shared'])) call_user_func(static::$composers['shared'], $view); - - if (isset(static::$composers[$view->view])) - { - foreach ((array) static::$composers[$view->view] as $key => $value) - { - if ($value instanceof \Closure) return call_user_func($value, $view); - } - } - } - -} - -/** - * Load the application's composers into the composers property. - */ -Composer::$composers = require APP_PATH.'composers'.EXT; \ No newline at end of file +} \ No newline at end of file diff --git a/public/index.php b/public/index.php index 7c03c0d8..44e94ffe 100644 --- a/public/index.php +++ b/public/index.php @@ -43,6 +43,4 @@ | 3... 2... 1... Lift-off! |-------------------------------------------------------------------------- */ -require $laravel.'/laravel.php'; - -echo number_format((microtime(true) - START_TIME) * 1000, 2); \ No newline at end of file +require $laravel.'/laravel.php'; \ No newline at end of file