-(defpsmacro let (bindings &body body)
- (flet ((add-renamed-vars (bindings predicate)
- (mapcar (lambda (x) (append x (list (ps-gensym (car x)))))
- (remove-if predicate bindings :key #'car)))
- (var (x) (first x))
- (val (x) (second x))
- (renamed (x) (third x)))
- (let* ((normalized-bindings (mapcar (lambda (x) (if (symbolp x) `(,x nil) x)) bindings))
- (lexical-bindings (add-renamed-vars normalized-bindings #'ps-special-variable-p))
- (dynamic-bindings (add-renamed-vars normalized-bindings (complement #'ps-special-variable-p)))
- (renamed-body `(symbol-macrolet ,(mapcar (lambda (x) (list (var x) (renamed x)))
- lexical-bindings)
- ,@body)))
- `(progn
- ,@(mapcar (lambda (x) `(var ,(renamed x) ,(val x))) lexical-bindings)
- ,(if dynamic-bindings
- `(progn ,@(mapcar (lambda (x) `(var ,(renamed x))) dynamic-bindings)
- (try (progn (setf ,@(loop for x in dynamic-bindings append
- `(,(renamed x) ,(var x)
- ,(var x) ,(val x))))
- ,renamed-body)
- (:finally
- (setf ,@(mapcan (lambda (x) `(,(var x) ,(renamed x))) dynamic-bindings)))))
- renamed-body)))))
+(define-ps-special-form let (bindings &body body)
+ `(js:let ,(mapcar #'car bindings)
+ ,@(let ((body-forms (if compile-expression?
+ `((progn
+ ,@(mapcar (lambda (bind)
+ `(var ,(car bind) ,(cadr bind)))
+ bindings)
+ ,@body))
+ `(,@(mapcar (lambda (bind)
+ `(var ,(car bind) ,(cadr bind)))
+ bindings)
+ ,@body))))
+ (mapcar #'ps-compile body-forms))))