en en en en en en en en en en en fr en en en en en en en en en en en en en en en en en de en en en de nl en en sv en de en en da da en de en de en de en de en de en en en en ja en en en en en en en de en en kn en en en en en en en en en en en en en en en en en en en en en en en en en en en en en en en en en en en en en en en fr en en en en ar en en en en en en en en en en en en en en en en en en en en en en en en en en en en en en en en en en en en en en en en en en en en en en en en en en en en en en en en fa en en en en en en en en en en en en en en en en en en en en en en en en en en id en en en
php-imagick: The image processing framework for PHP, if you want to use widget like auto Figure or Picture, this is the recommended plugin
php-gd: The image processing framework for PHP
If you just want to use the command line part of the Clips Tool. You'll just need php-clips installed first.
If you want to use web development framework. You'll need php-sass and at least 1 PHP image processing framework installed.
Then, add this code to your composer.json
Then, you can use composer to download it.
What is CLIPS? And why this framework?
The reason of writting this framework (part of it, the command line part), can be found at here.
This framework came out from a small framework to processing data using PHP.
It use CLIPS as its fundamental part, it try to create a flexiable environment like CI did, but honor the new standards in PHP 5.* and the PHP-FIG designed.
So, what is CLIPS then? Why I use it as the core of the framework?
For details of CLIPS, you can get it here.
CLIPS for me is a fast(yes, very fast) RETE based rule engine written in C, it use a dialect of lisp as its grammar.
You can use it to write very smart rule based program, I'll take a very simple example from the demo code of this framework.
Suppose you have a little blog website that has a dashboard to manage it. You don't really want anyone but you and your cowriters of this blog can view the dashboard.
So, you want the dashboard can be viewed only when logged in.
Here is the rules code to make this:
Let me explain it a little(for the details of CLIPS, you can get them here):
defrule: This command will define a rule and name it by the name you given it as the first parameter, for the upper example, I have a rule named only-users-logged-in-can-view-dashboard
Clips\SecurityItem: This is the framework object that framework generated automatically. For this example, it is the request that user's browser(so the type is an action), and the uri of this action.
test: Test if the fact matches this rule, in this example, it will let PHP function do this work, to test if the user is logged in or not
reject: This is the framework function, just let framework to know you want to reject this action with the reason of "Must logged in to view DashBoard!"
CLIPS can do lots more than this.
In fact, the core part of this framework, loading, configuration guessing, request routing, security checking are all done by rules.
Hello World? - Command Line
Since this framework can be framework of command line or web. Let's start from commandline.
clips-tool begin with a simple command line tool first, so using clips-tool to write a command line program is very easy.
Here is the steps:
Clone the clips-tool's code from here
Install the dependencies using composer
Add the path of clips (a bash script, window user can use cygwin to run it) to PATH, or create a soft link of that file to you bin folder
Run command clips version to test for it
Go to any folder, run clips generate command and follow the wizzard
After the steps above, you can get a folder named commands, and a file, say HelloCommand.php.
It should be something like this:
The content of the file should be something like this:
<?php in_array(__FILE__, get_included_files()) or exit("No direct sript access allowed"); use Clips\Command; /** * This is a simple command * * @author Jack * @version 1.0 * @date Sun Mar 8 21:31:40 2015 */ class HelloCommand extends Command { public function execute($args) { } }
And, yes, this is a very very simple command. But it has all the thing a command line command must have, the commandline args, and all the methods it get from base class command.
Pretty simple, say if we just want to print a welcome message (hello world). So, you can change the code to this;
output("Hello World!"); } }
Then using command clips hello to run it.
Let's begin with a little template thing.
Say you want to transfer a name to the hello world command, then you can change the code to this:
output(Clips\clips_out("string://Hello {{name}}", array('name' => Clips\get_default( $args, 0, "World")), false)); } }
This needs some explanation.
Clips uses mustache as its default template engine. So you can just using clips_out function located in Clips namespace to use it.
But, how mustache find the template?
Clips tool uses a simple Resource scheme based resource framework to find the resource.
If there is no scheme set for clips_out, it will use tpl:// by default(which will try every template path).
And in above example, the resource scheme is string://, so mustache will just use the string as the input resource. This is a little like PHP's resource handling frameowork, but more flexiable.
The second thing to explain is Clips\get_default.
This is a handy function, it will try the first argument (object or array), if it has the key(second argument), if so, it will return the value of that key, if not, it will return the default value (third argument).
Getting Enhanced - Command Line
So, how to start from here? For example, how we access the libraries that framework provided?
For example, what if you want to get the rule engine?
Let's start from a HelloRules Command, like this:
clips = $clips; } public function execute($args) { $this->clips->command('(defrule hello-world-rule (name ?name) => (printout t "Hello " ?name crlf))'); $this->clips->assertFacts(array('name', Clips\get_default($args, 0, 'world'))); $this->clips->run(); var_dump($this->clips->queryFacts()); } }
Let's look at the code in more details.
If you want clips to enhance your command, you just let your command implements the ClipsAware interface, and framework will set the clips reference to your command automatically
You can just run the clips command through clips's command method
You can interact to clips' facts just using assertFacts and queryFacts methods, the detail for these methods, you can view it here
The output of the command clips helloRules will be like this:
Hello world array(1) { [0]=> array(2) { [0]=> string(5) "world" ["__template__"]=> string(4) "name" } }
The same function like clips(request you to implement an interface to get the service you wanted) is:
Logger: The PSR-3 complaint logger
Tool: The clips tool itself
Getting More Enhanced - Command Line
It is cool to have your dependency just have a interface to implement.
But there is lots lots of objects in the framework, so how can you acces them? Implement interfaces one by one seems not be an great idea.
So, how can you get the depenency of your command?
It should be something like this:
output($this->markup->render("#This is h1")); } }
I used a framework library Markup as this exmple.
As you can see, the library dependency of this command, is just declared as an annotation of this command ( @Clips\Library("markup") ).
And after your declearation, framework will create and give the reference of that object to you as the name(lowercased) of the class name you have provided.
All the name you provided will be uppercase first before find the class, so you don't need to make the first letter uppercase. But if your class name is in camel case, DO preserve the upper case other than first letter.
For example, MyModel, should be myModel, not mymodel, or in file name case sensitive system like linux you won't get this class.
All the reference name of the object will be lowercase though (say MyModel will be mymodel).
Using only lowercase for reference name has 3 meanings:
The reference name is easy to identify and have small chances to override your command's fields (other fields are camel based)
Decrease the chances of miss typing for upper or lower cases
Auto fields are not means to read, but to use, if you don't like the name, you can just take a temp variable to reference it
Everything located in Libraries(no matter Clips or yours) will be load and created. If you wants to use namespace, look next chapter.
Other than Clips\Library, you can also use Clips\Model, Clips\Object to get the dependency you want.
Of cause, you shouldn't worry about the dependency of you dependency.
Command dependencies - Command Line
OK, now you know what you should do if you want to add dependency to your command. But wait, what if your command is based on another command?
Say, your package command will depends fetch command?
You can use @Clips\Depends to rescue. Use is just like the other annotations, and you can get the command executed right before your command.
How about configuration? - Command line
Our command is very simple for now, what if we want to connect to some database?
Or try to locate some file in some folder? How can we configure our command?
That's the power of clips-tool.
You can add your configuration in:
with name clips_tool.json. And if you have multiple of these, don't worry, clips-tool will get all the configurations to you(say, you have a /etc/clips_tools.json as system wide configuration, and a project's own configuration).
And the configuration should be something like this(a simple configuration from a demo site):
{ "table_prefix":"cms_", "namespace": ["Clips\\Cms\\"], "route_rules": ["/application/rules/route.rules", "/rules/route.rules"], "filters": ["Security", "Rules", "Form", "Scss", "Css", "SmartyView", "MustacheView", "JsonView", "DirectView"], "helpers":["web", "html"], "default_view": "Smarty", "debug_sass": true, "sass_preload": ["variables"], "models": { "demo": { "datasource": "mysql" } }, "logger": { "handlers": { "Stream" : ["php://stdin", "debug"], "FirePHP" : ["debug"], "ChromePHP": ["debug"], "RotatingFile": ["/tmp/clips_cms.log", 4, "debug"] }, "processors": ["Git", "PsrLogMessage", "Introspection", "Tag"] }, "datasources": { "mysql": { "table_prefix":"cms_", "type": "mysqli", "database": "cms_dev" } } }
As you can see, the configuration is no more than key => value json object.
And you can access any of your configuration at anywhere using Clips\config() function.
The Logging, Mate - Command line
Maybe you can see the logging configuration above(logging is using Monolog as its implementation).
The logger and handlers is same as monolog, but without useless words.
It is quite useful to use FirePHP or ChromePHP to debug, believe me.
How about namespaces? - Command line
Clips Tool is PSR-4 complaint framework, and it prefers you to write application using it.
So, how can Clips Tool can know what namespace you are using(or namespaces, because you can use as many plugins as possible).
The configuration comes to rescure. See the example above:
This configuration will told clips-tool, that you wants to use the classes located in Clips\Cms\ namespace.
So, for example, you want a model of Clips\Cms\Models\UserModel, you just can get the reference using @Clips\Model("user").
Same thing, if you have a Object like Clips\Cms\Libraries\Ldap, you can just get it using @Clips\Library("ldap").
All tne classes in clips-tools follow the (Models, Libraries rule), you can save lots of typing follow these rules.