Skip to content

Instantly share code, notes, and snippets.

@godDLL
Last active August 29, 2015 14:02
Show Gist options
  • Save godDLL/288ae2ca5b4617e21cf5 to your computer and use it in GitHub Desktop.
Save godDLL/288ae2ca5b4617e21cf5 to your computer and use it in GitHub Desktop.
AMD-style modules (as found in Javascript) for PHP >= 5.4
<?php /*! php-import v0.2.5 (c)2014 Yuli Che. <god.dll@icloud.com> @license MIT */
/*
* Javascript's AMD-style modules for PHP >= 5.4
*
*
* USAGE: you write code modules that are scope-isolated and export objects.
*
* <?php /*! PROJECT_URL v0.0.0 (c)2014 YOUR_NAME <YOUR_EMAIL> @license MIT *\/
* defined('PHP_IMPORT') or die(1);
* return new Object(array(
* 'name'=> 'my_module',
* 'get_name'=> function (){ return $this->name; }
* ));
*
*
* Your module could return a function that configures your object instead:
*
* return function ($opts){
* // we are ignoring $opts, which could be used to configure something here
* return object(['name'=>'my_module', 'get_name'=>function (){ return $this->name; }]);
* };
*
*
* In your other code modules, or in your index.php file you can get those objects by name:
*
* list($foo, $bar)= import(['foo', 'foo/bar']);
*
*
* Use a scope block to avoid making your own $vars global:
*
* call_user_func(function(){
* // any $vars inside tools/wrench.inc stay inside anyway
* $wrench = import('tools/wrench');
* // do something with $wrench, the object returned from tools/wrench.inc
* });
*
*/
defined('PHP_IMPORT_DIR') or define('PHP_IMPORT_DIR', dirname(__FILE__).'/');
defined('PHP_IMPORT_EXT') or define('PHP_IMPORT_EXT', '.inc');
define('PHP_IMPORT', '0.2.5');
class Object {
// A variant of stdClass with callable properties.
static function e ($exception, $errno=0){
echo $exception->getMessage(),
PHP_SAPI == 'cli' && empty($_SERVER['REMOTE_ADDR']) ? "\n" : '<br /><pre>',
strstr($exception->getTraceAsString(), "\n");
if ($errno) die($errno);
}
function __construct(array $proto=null){
if(! empty($proto))
foreach ($proto as $key=> $val)
$this->$key= $val;
}
function __call($func, array $args){
try {
if (is_callable($this->$func)){
return call_user_func_array($this->$func, $args);
} else {
throw new RunTimeException('Call to undefined method: '.$func.'()');
}
} catch (RunTimeException $e){
Object::e($e, 45);
}
}
function __set($key, $val){
if (is_callable($val)){
return $this->$key= $val->bindTo($this);
} else {
return $this->$key= $val;
}
}
function __get($key){
try {
if (isset($this->$key)){
return $this->$key;
} else {
throw new RunTimeException('Accessing undefined property: '.$key);
}
} catch (RunTimeException $e){
Object::e($e, 45);
}
}
}
function object($proto=null){ return new Object($proto); }
function import($depends){
// Caching variant of `require`, with scope leak protection (always on).
static $self= [];
if(! isset($self['import'])){
$self['import']= function ($module, &$self){
if (array_key_exists($module, $self))
return $self[$module];
$self[$module]= @include PHP_IMPORT_DIR.$module.PHP_IMPORT_EXT;
if(! $self[$module])
throw new RunTimeException('Can not import module: ' .PHP_IMPORT_DIR.$module.PHP_IMPORT_EXT);
return $self[$module];
};
}
try {
if(! is_array($depends))
return $self['import']($depends, $self);
$exports= [];
foreach ($depends as $module)
array_push($exports, $self['import']($module, $self));
return $exports;
} catch (RunTimeException $e){
Object::e($e, 2);
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment