Scriptor / pharen

Lisp to PHP Compiler
http://pharen.org
BSD 3-Clause "New" or "Revised" License
218 stars 31 forks source link

chain operator -> don't expand macro on object chain #32

Closed francescoagati closed 13 years ago

francescoagati commented 13 years ago

with this code


(defmacro viewfactory (view)
  '(:: View (factory ~view))
 )

(local view (-> (viewfactory "page/3") (bind "content" content)))

(local (-> this request response) (-> view (render)))

is compiled in


Lexical::$scopes['oop'] = array();
$view = viewfactory("page/3")->bind("content", $content);
$this->request->response = $view->render();

macro viewfactory isn't expaned with ->

Scriptor commented 13 years ago

Yep, this is a fix for when methods have the same name as macros. Macro-expansion is deliberately prevented in method calls.

For example, there is the first macro, but sequences also have a method called first. Which should it pick? I'm leaning towards not doing macro-expansion inside method calls so that you can be sure you'll never run into this kind of issue. Think about it this way, when you do (-> obj (foo)) what you want to do is call the method foo, which belongs to obj. You don't want to worry about colliding with any macros that happen to have similar names as the object's methods. It seems Clojure does the same thing.

Unfortunately, this isn't perfect, since macros can help reduce boiler-plate code as in your example. viewfactory doesn't really need to be a macro and proper lisp style is to only use macros when absolutely necessary.

francescoagati commented 13 years ago

ok thanks for the clarification ;-)