There are a few interactive php shells out there, so I picked one and wrote a drush command that bootstraps a site and opens a php shell (similar to the sql cli command). The command is simply "php". Attached is a zip with all the necessary components.
The php shell code is available here: http://jan.kneschke.de/projects/php-shell
This shell supports readline if you have it, but works just as well without it. Additionally, you can customize it to your liking. I customized this one a bit by changing the output colors, and setting the $_ variable to contain the output from the previous command.
Using Drush with an interactive php shell is ridiculously powerful. I use it all the time to aid in development and debugging. Figured I'd share the tip. :-)
Comment | File | Size | Author |
---|---|---|---|
#29 | phprepl.tar_.gz | 3.46 KB | matt2000 |
#23 | drush_interactive_shell.patch | 2.15 KB | msonnabaum |
drush_phpshell.zip | 187.72 KB | srhaber |
Comments
Comment #1
moshe weitzman CreditAttribution: moshe weitzman commentedYeah, we surely want something like this. Please lets compare against #543550: Drush interactive mode and pick the best way forward.
Comment #2
srhaber CreditAttribution: srhaber commentedI would treat Drush interactive mode and PHP interactive mode as separate features. Drush mode interprets drush commands and is accessible for general users. PHP mode is reserved for raw php and used primarily by developers.
Comment #3
jonhattanYeah, my first impression was this issue is a duplicate but they target different things. This issue is as a third party integration into drush and problems and similarities of #543550: Drush interactive mode dont apply because they're implemented in `php-shell` and not in the provided drush command.
srhaber: you force colors for a black background. It should also be visible on console with white background. You can see how drush manage it in function `_drush_print_log()` at file includes/drush.inc.
It is also interesting to get some doc or examples as I wasn't able to do anything with your shell :S
Lastly, a related issue: #562888: The readline library
Comment #4
srhaber CreditAttribution: srhaber commentedjonhattan: Yeah I customized the shell a bit since I use a dark background. The shell is configurable and has a couple default color schemes you can access by typing one of the following commands:
>> :set background=light # Loads a color scheme suitable for white backgrounds
>> :set background=dark # Loads a color scheme suitable for black backgrounds
I'll look into adding an option to set the color scheme so it's a little more accessible. Until then, try using one of those :set background commands.
The shell degrades gracefully if you don't have readline support. However, if you do have readline, you'll be able to use the up/down arrow keys to view previous commands, use Ctrl-A/E to move around on the prompt, and most importantly use Tab auto-complete to view a list of all possible functions in the namespace.
Here are some sample commands. The shell will keep prompting new lines until all brackets are closed:
>> $u = user_load(1);
>> print_r($u);
>> if (variable_get('site_offline', 1)) {
.. drush_print('Site offline');
.. } else {
.. drush_print('Site online');
.. }
I've found the shell most useful for viewing user and node objects for debugging, and testing new code during module development.
Comment #5
moshe weitzman CreditAttribution: moshe weitzman commentedbeen playing with this again. an interesting feature, that sorta duplicates script command but perhaps different enough so they both merit inclusion.
a few needs:
* rename the command to php-cli
* let command table light or dark scheme as an argument?
* perhaps do something about readline as per #562888: The readline library. my macports php seems not to have it.
Comment #6
srhaber CreditAttribution: srhaber commentedThanks for the suggestions Moshe!
I did a little cleanup on this project. The source is available on Github.
http://github.com/srhaber/drush_php_cli
* Renamed the command to php-cli.
* Removed the color feature completely so it uses the terminal default settings.
I'll take a look at the Readline thread. Is there something to look out for specifically? This shell degrades gracefully if it can't find readline. You just won't be able to make use of tab-completion, command history, etc.
There is a Facebook project called phpsh which emulates readline functionality in a php shell. It's written in Python however, so it may be a challenge to integrate with Drush.
http://www.phpsh.org/
I'm not sure what the proper "etiquette" is for using a third-party library in a Drupal project. As a courtesy I could reach out to the original developer. Thoughts?
Also, apologies for the *super late* response here. My job keeps me busy. :-)
Comment #7
izmeez CreditAttribution: izmeez commentedsubscribing
Comment #8
mariomaric CreditAttribution: mariomaric commentedSubscribing.
Comment #9
jennifer.chang CreditAttribution: jennifer.chang commentedsubscribe.
Comment #10
okokokok CreditAttribution: okokokok commentedGreat feature!
It would be very useful to be able to switch between the available cli's drush is offering.
Most useful to me seems a possibility to quickly go into sql-cli from the php-cli.
I love Python but it doesn't seem right to depend on it for php-cli to work.
Comment #11
maherg CreditAttribution: maherg commentedsubscribe.
Comment #12
greg.1.anderson CreditAttribution: greg.1.anderson commentedThis was brought up again in #952234: REPL code (marked as duplicate). It occurs to me that perhaps this command could be implemented to just use
php -a
to run php in interactive mode.Comment #13
progga CreditAttribution: progga commentedI see that srhaber's php-cli is better than what I have submitted. Since "php -a" is unfortunately not a substitute for a Drupal REPL, php-cli should be included unless its dependency on a PEAR library is a problem. Thanks.
Comment #14
greg.1.anderson CreditAttribution: greg.1.anderson commentedWhy isn't php -a an adequate substitute? It seems that drush could re-launch php -a with a system call, and execute the bootstrap code via --process-begin or --process-file. Then you would get all of the readline goodness and other features of php -a without needing to re-implement it.
Comment #15
jonhattanAFAIK
php -a
is not an option because there's no way to use it after bootstrap. It is a toy that always starts in a clean state. You can't dophp -a drush.php
norphp -a < drush.php
.OTOH #562888: The readline library is blocker. If there's no readline it is almost useless. Mmm I think Yoran Brault did something interesting (only for unixes) by using
stty
.Comment #16
greg.1.anderson CreditAttribution: greg.1.anderson commentedI'm pretty sure that
php -a
will work just fine, but I suppose I'll have to prove it with a patch. :)Comment #17
jonhattanI'll love to see such a patch. Note
php -a -f file.php
is neither an option :)Comment #18
greg.1.anderson CreditAttribution: greg.1.anderson commentedphp -a --process-begin
should work, though, presuming that you pass in a function call to the bootstrap code as the value to --process-begin.Comment #19
jonhattanI didn't know about --process-begin but I think it is neither an option :(
Some tests:
no way to make it work...
^^ it seems -a is exclusive.
I've read the implementation. If I'm not wrong, it confirms both options are mutually exclusive.
http://gcov.php.net/PHP_HEAD/lcov_html/var/php_gcov/PHP_HEAD/sapi/cli/ph...
param_mode_conflict
is:Comment #20
greg.1.anderson CreditAttribution: greg.1.anderson commentedDarn! I guess php -a really is a toy. :{ Submit a patch to php? :P (I know, we don't want to adjust the version of php that drush depends on...)
I guess it's back to fretting about readline availability, then.
Comment #21
progga CreditAttribution: progga commentedActually, when I originally wrote my Drupal REPL in Unix, I wrote it with readline support. Then Facebook's phpsh was released making my code unnecessary. Recently I have started to work at a new place (defaqto.com, who are still hiring) which is a Windows shop and so phpsh would not run. So I dropped the readline calls from my old Drupal REPL code and started using it alongside drush.bat. If you are using Window's command prompt, then you get some readline type functionality built-in (e.g. pressing the up arrow will bring the previous line). So I don't miss the readline functionality much apart from command history. This makes my code mostly relevant to Windows and so I submitted the code to the drush_extra project instead of the drush project. Hope this explains it a bit. Thanks.
Comment #22
greg.1.anderson CreditAttribution: greg.1.anderson commentedI don't have any interest in writing an interactive shell in drush; since php -a won't work, there is no way to make an interactive php mode the same way that drush core-cli works. So, we're back to #6. This command is welcome here, but I won't be working on it.
Comment #23
msonnabaum CreditAttribution: msonnabaum commentedI've been thinking about this lately (its something I've wanted for a while), and I think we can do it fairly easily if we leverage facebook's phpsh:
http://www.phpsh.org/
Attached is a POC drush command that bootstraps the site you run `drush interactive-shell` from. Very rough, but seems to work in my limited testing.
Comment #24
progga CreditAttribution: progga commentedJust wanted to mention "rlwrap" (http://utopia.knoware.nl/~hlub/uck/rlwrap/rlwrap.html). By wrapping your command in rlwrap (e.g. "rlwrap drush cli", you can get all the readline functionalities. "rlwrap" works in Unix and also under Cygwin. The windows cmd.exe provides line history functionality out of the box, so the absence of rlwrap on Windows is not a problem either.
Comment #25
ilo CreditAttribution: ilo commented#23 phpsh makes python a requirement for this to work and #24 rlwrap description says: 'rlwrap is a wrapper that uses the GNU readline library to allow the editing of keyboard input for any other command', so using readline seems no need for rlwrap in this case, I guess..
Looking forward the advances on this.
Comment #26
zroger CreditAttribution: zroger commentedI'm in favor of using phpsh. I started a sandbox project (http://drupal.org/sandbox/rz/1100042) before I was pointed to this thread that makes this type of functionality a drush add-on. I've been using this implementation for about a week now and find it very useful. IMHO, it would be a monumental task to match the existing level of functionality in phpsh.
Comment #27
zroger CreditAttribution: zroger commentedUpdate on phpsh. I have a full project going at http://drupal.org/project/phpsh.
Comment #28
matt2000 CreditAttribution: matt2000 commentedAnother entry to the field:
https://github.com/matt2000/phprepl
It's a PHP-REPL that just happens to have a wrapper that bootstraps Drupal using Drush.
Comment #29
matt2000 CreditAttribution: matt2000 commentedI've added a drush.inc file to phprepl, though that method of launching the shell does not currently support history and tab completion. This could be fixed with a small patch to drush which I recently discussed with Owen Barton.
A few notes on the differences between phprepl and phpshell from the OP's version:
- phprepl uses rlwrap as discussed above to avoid direct dependency on readline
- the php part of phprepl is one relatively short php file, so it's simpler.
- It's not "third-party" per se. I'd happily host the project on d.o and deprecate the github repo. I started to write it as a drush shell specificially, and realized it was cleaner to make the drupal bootstrap a simple wrapper around a general php shell.
- phprepl has some features phpshell lacks -- e.g., support for use of the global keyword, the ability to drop to a multi-line editor (assuming nlwrap is available), simpler syntax for function calls with no arguments; just type 'conf_path' for the equiavlent of 'echo conf_path();'
- On the plus side for phpshell, it looks like it's doing some validation on the input. phprepl currently will try to shove just about anything through eval().
-phpshell also handles fatal errors better.
Unfortunately, I did not find this thread or phpshell before I started writing my own tool, or I would have made an effort to build from that, so there is definitely overlap.
As for phpsh, it looks nice, but I assumed adding a python dependency was a non-starter for the possibility of inclusion in drush.
A tarball is attached for convenience of review.
Comment #30
RobLoachIf we had #1316322: Add PSR-0 autoloader to drush, Drush could automagically download PHP-REPL for us when needed.
Comment #31
msonnabaum CreditAttribution: msonnabaum commentedTried phprepl. Not impressed. The installer requiring sudo for what it's doing is a not reasonable IMO. If it worked with pear or composer, maybe.
Also, python as a dependency for phpsh is in no way a non-starter. Everyone has it installed and phpsh is a very solid project. I'm still in favor of integrating with it.
Comment #32
greg.1.anderson CreditAttribution: greg.1.anderson commentedOkay, maybe everyone does have python installed, but this is what I had to do to make phpsh work on my system:
The documentation wasn't clear on where to get easy_install (python-pip), Python.h (python-dev) or ncurses (libncurses5-dev), but the internets helped me. I already have a million packages (well, seems like) installed, so others might need to a little more searching. It is somewhat ironic that "easy_install" runs gcc, and in no way helps you with dependencies. You don't need 'sudo' to run
python setup.py install
, as it will install locally if you want; however, you do need sudo to get the dependencies you need to compile, if they're not pre-loaded. I don't think that's much of an issue, though.Once it was installed, though, phpsh, and the Drush phpsh extension pretty well rocked (although why the phpsh Drush command is 'console' instead of 'phpsh' is a mystery to me). I really like the built-in php documentation help feature. It would also be cool if there would be some way to integrate fn-hook and fn-view from devel into phpsh; I did not look into what it would take to extend. I suppose I could always run with two terminals open -- one with bash, and one with phpsh.
Sure would be nice to have a better installer for phpsh; all the same, I wouldn't be opposed to integrating with the Drush phpsh extension if there was a desire to move in that direction.
Comment #33
didlix CreditAttribution: didlix commentedI've got this setup, but when I try to do anything that I would expect to be working in drupal I get errors that the functions don't exist.
Error: Call to undefined function node_load() in /usr/share/php/phprepl/phprepl.php(105) : eval()'d code, line 1
It looks like you're doing a full bootstrap, maybe my understanding of what this gives me is wrong?
Comment #34
matt2000 CreditAttribution: matt2000 commented@didlix
It works for me.... Can you provide the exact steps to reproduce the error? Make sure you are running the command as `drepl`.
Comment #35
matt2000 CreditAttribution: matt2000 commenteddidlix's issue hasn't been reporduced.
msonnabaum's complaint isn't valid. (installing an app for all users always requires root access, and phprepl doesn't require being installed this way. If it becomes part of Drush, it will be available via PEAR because drush is.)
So is there any consensus on the best way forward among
a.) phpsh (in python)
b.) phpshell (in PHP)
c.) phprepl / drepl (in PHP+BASH)
?
I'm willing to continue to support phprepl, but don't want to waste effort if the community is favoring another choice.
Comment #36
greg.1.anderson CreditAttribution: greg.1.anderson commentedI don't think that we should
use anythingpackage anything into Drush core that is less functional than phpsh. I suspect it would be more efficient to concentrate on collaborating with the more functional projects than to reimplement in php, but that is just my opinion.Comment #37
moshe weitzman CreditAttribution: moshe weitzman commentedI'm not bothered by the Python dependency. I'd love to have http://drupal.org/project/phpsh in Drush core.
Comment #38
moshe weitzman CreditAttribution: moshe weitzman commentedComment #39
kscheirerFor what it's worth, I checked our srhaber's code (#6) from the git repo and everything worked great. No install of anything required, up and running in 5 minutes.
Comment #40
Jody LynnI'm a big user of http://drupal.org/project/phpsh and would love to see it in drush core. I freak out when people don't have it installed and I have to resort to drush php-eval or /devel/php.
Comment #41
dinofile CreditAttribution: dinofile commentedthanks. Worked like a treat for me too. Very cool.
Comment #42
holtzermann17 CreditAttribution: holtzermann17 commentedI installed phpsh and the corresponding module: it's "nice" but doesn't work out of the box: #1932556: Drupal fails to bootstrap
Comment #43
holtzermann17 CreditAttribution: holtzermann17 commentedA further note to #42 - phpsh doesn't seem to work well when xdebug is turned on, see for instance https://github.com/facebook/phpsh/issues/41 and other related issues in the phpsh tracker. It seems like the phpsh developers somehow intended that the two systems play well together, but at the moment they really don't!
Comment #44
greg.1.anderson CreditAttribution: greg.1.anderson commentedAnother option: https://github.com/d11wtq/boris
(From a tweet by @moshe weitzman)
Comment #45
yched CreditAttribution: yched commentedAnd a drupal loader for boris (#44) : https://github.com/tobiassjosten/boris-loader
Pretty awesome...
Comment #46
moshe weitzman CreditAttribution: moshe weitzman commentedPerhaps all we need is a small wrapper around #45 that launches boris in the right drupal site. Would be nice if it worked for remote sites as well, like core-ssh command.
I'm closing this issue in favor of discussion at https://github.com/drush-ops/drush/issues/11. Lets work there.
Comment #47
patcon CreditAttribution: patcon commentedI absolutely LOVE that this conversation has moved to github...! MUHAHAHA