Setting variables in hamlet forall

I noticed a pattern that in hamlet $forall i often retrieve the same value from a map, Sometimes 3,4 times. $forall row <- rs <td>#{getStr "form_name" row} <td>#{getStr "docname" row} ... <td>#{fromMaybe "" (IntMap.lookup (getInt "form_id" row) counties)} <td>#{fromMaybe "" (IntMap.lookup (getInt "form_id" row) customers)} Would it be possible to allow let statement in forall for often used values ? Regards, Vagif Verdi

I've been very hesitant about adding more features to Hamlet, especially
ones that are already implemented in Haskell. That's been my reasoning for
avoiding any kind of variable definitions until now. However, this does seem
like a compelling use case.
I don't think it would make sense to limit it to foralls: it makes as much
sense in maybes, and I think it would be confusing if it only applied in
some cases. As for syntax, how about:
$forall row <- rs
$let formId = fromMaybe "" $ IntMap.lookup $ getInt "form_id" row
...
I'm not 100% sold on this yet, what does everyone else think?
One last note: I'm probably going to be announcing a feature freeze on Yesod
0.8 *very* soon, and making a beta release to Yackage so that people can
test. If you have any last-minute input, now's the time. I'm planning on
giving the beta test period about a week, and then releasing to Hackage.
Michael
On Thu, Apr 7, 2011 at 2:57 AM,
I noticed a pattern that in hamlet $forall i often retrieve the same value from a map, Sometimes 3,4 times.
$forall row <- rs <td>#{getStr "form_name" row} <td>#{getStr "docname" row} ... <td>#{fromMaybe "" (IntMap.lookup (getInt "form_id" row) counties)} <td>#{fromMaybe "" (IntMap.lookup (getInt "form_id" row) customers)}
Would it be possible to allow let statement in forall for often used values ?
Regards, Vagif Verdi
_______________________________________________ web-devel mailing list web-devel@haskell.org http://www.haskell.org/mailman/listinfo/web-devel

put me in the opposed category. You can just as easily put: let formId rs = fromMaybe "" $ lookup $... in the haskell function that loads the hamlet file then you just have to put #{formId rs} in the hamlet. I think adding syntax should be done only when very necessary. seems like a very small win here at a big cost. yes, if you have a situation where many handlers are calling the same hamlet file, there might be some duplication, but then you can always raise the formId function to a top-level function. max On Apr 7, 2011, at 5:15 PM, Michael Snoyman wrote:
I've been very hesitant about adding more features to Hamlet, especially ones that are already implemented in Haskell. That's been my reasoning for avoiding any kind of variable definitions until now. However, this does seem like a compelling use case.
I don't think it would make sense to limit it to foralls: it makes as much sense in maybes, and I think it would be confusing if it only applied in some cases. As for syntax, how about:
$forall row <- rs $let formId = fromMaybe "" $ IntMap.lookup $ getInt "form_id" row ...
I'm not 100% sold on this yet, what does everyone else think?
One last note: I'm probably going to be announcing a feature freeze on Yesod 0.8 *very* soon, and making a beta release to Yackage so that people can test. If you have any last-minute input, now's the time. I'm planning on giving the beta test period about a week, and then releasing to Hackage.
Michael
On Thu, Apr 7, 2011 at 2:57 AM,
wrote: I noticed a pattern that in hamlet $forall i often retrieve the same value from a map, Sometimes 3,4 times. $forall row <- rs <td>#{getStr "form_name" row} <td>#{getStr "docname" row} ... <td>#{fromMaybe "" (IntMap.lookup (getInt "form_id" row) counties)} <td>#{fromMaybe "" (IntMap.lookup (getInt "form_id" row) customers)}
Would it be possible to allow let statement in forall for often used values ?
Regards, Vagif Verdi
_______________________________________________ web-devel mailing list web-devel@haskell.org http://www.haskell.org/mailman/listinfo/web-devel
_______________________________________________ web-devel mailing list web-devel@haskell.org http://www.haskell.org/mailman/listinfo/web-devel

On Thu, Apr 7, 2011 at 7:51 PM, Max Cantor
put me in the opposed category.
You can just as easily put: let formId rs = fromMaybe "" $ lookup $...
in the haskell function that loads the hamlet file then you just have to put #{formId rs}
in the hamlet. I think adding syntax should be done only when very necessary. seems like a very small win here at a big cost.
Where is the cost? Most of the effort would be just glueing together some pieces of existing code. Given that there are already two places where hamlet does variable binding, adding a third will not hurt it, or perhaps a single more expressive form of variable binding is required. Something like monadic bind (>>=) where you can bind non-monadic values using the identity monad.
yes, if you have a situation where many handlers are calling the same hamlet file, there might be some duplication, but then you can always raise the formId function to a top-level function.
max
On Apr 7, 2011, at 5:15 PM, Michael Snoyman wrote:
I've been very hesitant about adding more features to Hamlet, especially ones that are already implemented in Haskell. That's been my reasoning for avoiding any kind of variable definitions until now. However, this does seem like a compelling use case.
I don't think it would make sense to limit it to foralls: it makes as much sense in maybes, and I think it would be confusing if it only applied in some cases. As for syntax, how about:
$forall row <- rs $let formId = fromMaybe "" $ IntMap.lookup $ getInt "form_id" row ...
I'm not 100% sold on this yet, what does everyone else think?
One last note: I'm probably going to be announcing a feature freeze on Yesod 0.8 *very* soon, and making a beta release to Yackage so that people can test. If you have any last-minute input, now's the time. I'm planning on giving the beta test period about a week, and then releasing to Hackage.
Michael
On Thu, Apr 7, 2011 at 2:57 AM,
wrote: I noticed a pattern that in hamlet $forall i often retrieve the same value from a map, Sometimes 3,4 times. $forall row <- rs <td>#{getStr "form_name" row} <td>#{getStr "docname" row} ... <td>#{fromMaybe "" (IntMap.lookup (getInt "form_id" row) counties)} <td>#{fromMaybe "" (IntMap.lookup (getInt "form_id" row) customers)}
Would it be possible to allow let statement in forall for often used values ?
Regards, Vagif Verdi
_______________________________________________ web-devel mailing list web-devel@haskell.org http://www.haskell.org/mailman/listinfo/web-devel
_______________________________________________ web-devel mailing list web-devel@haskell.org http://www.haskell.org/mailman/listinfo/web-devel
_______________________________________________ web-devel mailing list web-devel@haskell.org http://www.haskell.org/mailman/listinfo/web-devel
-- -barkmadley sent from an internet enabled device

On Thu, Apr 7, 2011 at 10:34 PM, Mark Bradley
On Thu, Apr 7, 2011 at 7:51 PM, Max Cantor
wrote: put me in the opposed category.
You can just as easily put: let formId rs = fromMaybe "" $ lookup $...
in the haskell function that loads the hamlet file then you just have to put #{formId rs}
in the hamlet. I think adding syntax should be done only when very necessary. seems like a very small win here at a big cost.
Where is the cost? Most of the effort would be just glueing together some pieces of existing code. Given that there are already two places where hamlet does variable binding, adding a third will not hurt it, or perhaps a single more expressive form of variable binding is required. Something like monadic bind (>>=) where you can bind non-monadic values using the identity monad.
An example: $bind row <- rs $bind formId <- Identity $ fromMaybe "" $ IntMap.lookup $ getInt "form_id" row <td>#{formId counties} <td>#{formId customers} It could also be possible to do else cases where it didn't bind: -- list bind $bind row <- rs -- identity bind $bind formId <- Identity $ fromMaybe "" $ IntMap.lookup $ getInt "form_id" row <td>#{formId counties} <td>#{formId customers} -- maybe bind $bind someValue <- someMaybeValue <div>content -- maybe value was Nothing $nobind <div>other content -- not possible with identity bind possible place for error/warning $nobind <div>This should not happen! -- empty list $nobind <div>i left my content in my other pants
yes, if you have a situation where many handlers are calling the same hamlet file, there might be some duplication, but then you can always raise the formId function to a top-level function.
max
On Apr 7, 2011, at 5:15 PM, Michael Snoyman wrote:
I've been very hesitant about adding more features to Hamlet, especially ones that are already implemented in Haskell. That's been my reasoning for avoiding any kind of variable definitions until now. However, this does seem like a compelling use case.
I don't think it would make sense to limit it to foralls: it makes as much sense in maybes, and I think it would be confusing if it only applied in some cases. As for syntax, how about:
$forall row <- rs $let formId = fromMaybe "" $ IntMap.lookup $ getInt "form_id" row ...
I'm not 100% sold on this yet, what does everyone else think?
One last note: I'm probably going to be announcing a feature freeze on Yesod 0.8 *very* soon, and making a beta release to Yackage so that people can test. If you have any last-minute input, now's the time. I'm planning on giving the beta test period about a week, and then releasing to Hackage.
Michael
On Thu, Apr 7, 2011 at 2:57 AM,
wrote: I noticed a pattern that in hamlet $forall i often retrieve the same value from a map, Sometimes 3,4 times. $forall row <- rs <td>#{getStr "form_name" row} <td>#{getStr "docname" row} ... <td>#{fromMaybe "" (IntMap.lookup (getInt "form_id" row) counties)} <td>#{fromMaybe "" (IntMap.lookup (getInt "form_id" row) customers)}
Would it be possible to allow let statement in forall for often used values ?
Regards, Vagif Verdi
_______________________________________________ web-devel mailing list web-devel@haskell.org http://www.haskell.org/mailman/listinfo/web-devel
_______________________________________________ web-devel mailing list web-devel@haskell.org http://www.haskell.org/mailman/listinfo/web-devel
_______________________________________________ web-devel mailing list web-devel@haskell.org http://www.haskell.org/mailman/listinfo/web-devel
-- -barkmadley sent from an internet enabled device
-- -barkmadley sent from an internet enabled device

A few points:
1) The cost is twofold: making Hamlet more complex from a user perspective,
and making the codebase more complex. I'm not a fan of either, unless it's
really justified.
2) I'm not really certain how your example below works as far as
disambiguating Maybe versus [] (i.e., $maybe versus $forall), but if we're
willing to go in this direction, you already have $let for free:
$forall foo <- foos
$forall foobar <- return $ bar foo
#{foobar}
Here, return would be for the [] instance of Monad. We could also use
$maybe, using the Maybe instance of Monad.
Michael
On Thu, Apr 7, 2011 at 3:46 PM, Mark Bradley
On Thu, Apr 7, 2011 at 7:51 PM, Max Cantor
wrote: put me in the opposed category.
You can just as easily put: let formId rs = fromMaybe "" $ lookup $...
in the haskell function that loads the hamlet file then you just have to
On Thu, Apr 7, 2011 at 10:34 PM, Mark Bradley
wrote: put #{formId rs}
in the hamlet. I think adding syntax should be done only when very necessary. seems like a very small win here at a big cost.
Where is the cost? Most of the effort would be just glueing together some pieces of existing code. Given that there are already two places where hamlet does variable binding, adding a third will not hurt it, or perhaps a single more expressive form of variable binding is required. Something like monadic bind (>>=) where you can bind non-monadic values using the identity monad.
An example:
$bind row <- rs $bind formId <- Identity $ fromMaybe "" $ IntMap.lookup $ getInt "form_id" row <td>#{formId counties} <td>#{formId customers}
It could also be possible to do else cases where it didn't bind:
-- list bind $bind row <- rs -- identity bind $bind formId <- Identity $ fromMaybe "" $ IntMap.lookup $ getInt "form_id" row <td>#{formId counties} <td>#{formId customers} -- maybe bind $bind someValue <- someMaybeValue <div>content -- maybe value was Nothing $nobind <div>other content -- not possible with identity bind possible place for error/warning $nobind <div>This should not happen!
-- empty list $nobind <div>i left my content in my other pants
yes, if you have a situation where many handlers are calling the same
max
On Apr 7, 2011, at 5:15 PM, Michael Snoyman wrote:
I've been very hesitant about adding more features to Hamlet,
especially ones that are already implemented in Haskell. That's been my reasoning for avoiding any kind of variable definitions until now. However,
hamlet file, there might be some duplication, but then you can always raise the formId function to a top-level function. this does seem like a compelling use case.
I don't think it would make sense to limit it to foralls: it makes as
much sense in maybes, and I think it would be confusing if it only applied in some cases. As for syntax, how about:
$forall row <- rs $let formId = fromMaybe "" $ IntMap.lookup $ getInt "form_id" row ...
I'm not 100% sold on this yet, what does everyone else think?
One last note: I'm probably going to be announcing a feature freeze on
Yesod 0.8 *very* soon, and making a beta release to Yackage so that people can test. If you have any last-minute input, now's the time. I'm planning on giving the beta test period about a week, and then releasing to Hackage.
Michael
On Thu, Apr 7, 2011 at 2:57 AM,
wrote: I noticed a pattern that in hamlet $forall i often retrieve the same value
from a map, Sometimes 3,4 times.
$forall row <- rs <td>#{getStr "form_name" row} <td>#{getStr "docname" row} ... <td>#{fromMaybe "" (IntMap.lookup (getInt "form_id" row) counties)} <td>#{fromMaybe "" (IntMap.lookup (getInt "form_id" row) customers)}
Would it be possible to allow let statement in forall for often used values ?
Regards, Vagif Verdi
_______________________________________________ web-devel mailing list web-devel@haskell.org http://www.haskell.org/mailman/listinfo/web-devel
_______________________________________________ web-devel mailing list web-devel@haskell.org http://www.haskell.org/mailman/listinfo/web-devel
_______________________________________________ web-devel mailing list web-devel@haskell.org http://www.haskell.org/mailman/listinfo/web-devel
-- -barkmadley sent from an internet enabled device
-- -barkmadley sent from an internet enabled device

On Thu, Apr 7, 2011 at 11:22 PM, Michael Snoyman
A few points: 1) The cost is twofold: making Hamlet more complex from a user perspective, and making the codebase more complex. I'm not a fan of either, unless it's really justified. 2) I'm not really certain how your example below works as far as disambiguating Maybe versus [] (i.e., $maybe versus $forall), but if we're willing to go in this direction, you already have $let for free: $forall foo <- foos $forall foobar <- return $ bar foo #{foobar}
I was really going out there with my suggestions and examples. The real benefit of a unified approach is that you can extend it to apply to your custom container types. Making it pretty similar to foldable but with an default behaviour when the data structure is empty. Also if you already have let for free using forall and return, why not make a sugared version that compiles down to that?
Here, return would be for the [] instance of Monad. We could also use $maybe, using the Maybe instance of Monad. Michael
On Thu, Apr 7, 2011 at 3:46 PM, Mark Bradley
wrote: On Thu, Apr 7, 2011 at 10:34 PM, Mark Bradley
wrote: On Thu, Apr 7, 2011 at 7:51 PM, Max Cantor
wrote: put me in the opposed category.
You can just as easily put: let formId rs = fromMaybe "" $ lookup $...
in the haskell function that loads the hamlet file then you just have to put #{formId rs}
in the hamlet. I think adding syntax should be done only when very necessary. seems like a very small win here at a big cost.
Where is the cost? Most of the effort would be just glueing together some pieces of existing code. Given that there are already two places where hamlet does variable binding, adding a third will not hurt it, or perhaps a single more expressive form of variable binding is required. Something like monadic bind (>>=) where you can bind non-monadic values using the identity monad.
An example:
$bind row <- rs $bind formId <- Identity $ fromMaybe "" $ IntMap.lookup $ getInt "form_id" row <td>#{formId counties} <td>#{formId customers}
It could also be possible to do else cases where it didn't bind:
-- list bind $bind row <- rs -- identity bind $bind formId <- Identity $ fromMaybe "" $ IntMap.lookup $ getInt "form_id" row <td>#{formId counties} <td>#{formId customers} -- maybe bind $bind someValue <- someMaybeValue <div>content -- maybe value was Nothing $nobind <div>other content -- not possible with identity bind possible place for error/warning $nobind <div>This should not happen!
-- empty list $nobind <div>i left my content in my other pants
yes, if you have a situation where many handlers are calling the same hamlet file, there might be some duplication, but then you can always raise the formId function to a top-level function.
max
On Apr 7, 2011, at 5:15 PM, Michael Snoyman wrote:
I've been very hesitant about adding more features to Hamlet, especially ones that are already implemented in Haskell. That's been my reasoning for avoiding any kind of variable definitions until now. However, this does seem like a compelling use case.
I don't think it would make sense to limit it to foralls: it makes as much sense in maybes, and I think it would be confusing if it only applied in some cases. As for syntax, how about:
$forall row <- rs $let formId = fromMaybe "" $ IntMap.lookup $ getInt "form_id" row ...
I'm not 100% sold on this yet, what does everyone else think?
One last note: I'm probably going to be announcing a feature freeze on Yesod 0.8 *very* soon, and making a beta release to Yackage so that people can test. If you have any last-minute input, now's the time. I'm planning on giving the beta test period about a week, and then releasing to Hackage.
Michael
On Thu, Apr 7, 2011 at 2:57 AM,
wrote: I noticed a pattern that in hamlet $forall i often retrieve the same value from a map, Sometimes 3,4 times. $forall row <- rs <td>#{getStr "form_name" row} <td>#{getStr "docname" row} ... <td>#{fromMaybe "" (IntMap.lookup (getInt "form_id" row) counties)} <td>#{fromMaybe "" (IntMap.lookup (getInt "form_id" row) customers)}
Would it be possible to allow let statement in forall for often used values ?
Regards, Vagif Verdi
_______________________________________________ web-devel mailing list web-devel@haskell.org http://www.haskell.org/mailman/listinfo/web-devel
_______________________________________________ web-devel mailing list web-devel@haskell.org http://www.haskell.org/mailman/listinfo/web-devel
_______________________________________________ web-devel mailing list web-devel@haskell.org http://www.haskell.org/mailman/listinfo/web-devel
-- -barkmadley sent from an internet enabled device
-- -barkmadley sent from an internet enabled device
-- -barkmadley sent from an internet enabled device

On Fri, Apr 8, 2011 at 2:47 AM, Mark Bradley
A few points: 1) The cost is twofold: making Hamlet more complex from a user
On Thu, Apr 7, 2011 at 11:22 PM, Michael Snoyman
wrote: perspective, and making the codebase more complex. I'm not a fan of either, unless it's really justified. 2) I'm not really certain how your example below works as far as disambiguating Maybe versus [] (i.e., $maybe versus $forall), but if we're willing to go in this direction, you already have $let for free: $forall foo <- foos $forall foobar <- return $ bar foo #{foobar}
I was really going out there with my suggestions and examples. The real benefit of a unified approach is that you can extend it to apply to your custom container types. Making it pretty similar to foldable but with an default behaviour when the data structure is empty.
Actually, forgetting the rest of the discussion here, I think extending $forall to work on any Foldable is a great idea. Any objections?
Also if you already have let for free using forall and return, why not make a sugared version that compiles down to that?
I haven't looked at your patch yet (thank you btw), but my concern is that introducing $let, the same way it's used in Haskell, introduces scoping issues that we don't otherwise have. $forall and $maybe already add a significant complexity to deal with the bound variable names, but at least it's bound for only the inner block. With $let, we would want it to be bound for the remainder of the block most likely. So we'd have two choices:
* Implement a whole bunch of complexity defining and implementing new scoping rules. * Have totally different semantics from Haskell. I'm not sure which approach your patch took. But maybe the problem was with my choice of name ($let); $with would likely make more sense for the inner block approach. But even so, I'm still concerned that this is complexity without enough reward.
Here, return would be for the [] instance of Monad. We could also use $maybe, using the Maybe instance of Monad. Michael
On Thu, Apr 7, 2011 at 3:46 PM, Mark Bradley
wrote: On Thu, Apr 7, 2011 at 10:34 PM, Mark Bradley
wrote: On Thu, Apr 7, 2011 at 7:51 PM, Max Cantor
put me in the opposed category.
You can just as easily put: let formId rs = fromMaybe "" $ lookup $...
in the haskell function that loads the hamlet file then you just have to put #{formId rs}
in the hamlet. I think adding syntax should be done only when very necessary. seems like a very small win here at a big cost.
Where is the cost? Most of the effort would be just glueing together some pieces of existing code. Given that there are already two places where hamlet does variable binding, adding a third will not hurt it, or perhaps a single more expressive form of variable binding is required. Something like monadic bind (>>=) where you can bind non-monadic values using the identity monad.
An example:
$bind row <- rs $bind formId <- Identity $ fromMaybe "" $ IntMap.lookup $ getInt "form_id" row <td>#{formId counties} <td>#{formId customers}
It could also be possible to do else cases where it didn't bind:
-- list bind $bind row <- rs -- identity bind $bind formId <- Identity $ fromMaybe "" $ IntMap.lookup $ getInt "form_id" row <td>#{formId counties} <td>#{formId customers} -- maybe bind $bind someValue <- someMaybeValue <div>content -- maybe value was Nothing $nobind <div>other content -- not possible with identity bind possible place for error/warning $nobind <div>This should not happen!
-- empty list $nobind <div>i left my content in my other pants
yes, if you have a situation where many handlers are calling the same hamlet file, there might be some duplication, but then you can always
raise
the formId function to a top-level function.
max
On Apr 7, 2011, at 5:15 PM, Michael Snoyman wrote:
I've been very hesitant about adding more features to Hamlet, especially ones that are already implemented in Haskell. That's been my reasoning for avoiding any kind of variable definitions until now. However, this does seem like a compelling use case.
I don't think it would make sense to limit it to foralls: it makes as much sense in maybes, and I think it would be confusing if it only applied in some cases. As for syntax, how about:
$forall row <- rs $let formId = fromMaybe "" $ IntMap.lookup $ getInt "form_id" row ...
I'm not 100% sold on this yet, what does everyone else think?
One last note: I'm probably going to be announcing a feature freeze on Yesod 0.8 *very* soon, and making a beta release to Yackage so that
can test. If you have any last-minute input, now's the time. I'm
wrote: people planning on
giving the beta test period about a week, and then releasing to Hackage.
Michael
On Thu, Apr 7, 2011 at 2:57 AM,
wrote: I noticed a pattern that in hamlet $forall i often retrieve the same value from a map, Sometimes 3,4 times. $forall row <- rs <td>#{getStr "form_name" row} <td>#{getStr "docname" row} ... <td>#{fromMaybe "" (IntMap.lookup (getInt "form_id" row) counties)} <td>#{fromMaybe "" (IntMap.lookup (getInt "form_id" row) customers)}
Would it be possible to allow let statement in forall for often used values ?
Regards, Vagif Verdi
_______________________________________________ web-devel mailing list web-devel@haskell.org http://www.haskell.org/mailman/listinfo/web-devel
_______________________________________________ web-devel mailing list web-devel@haskell.org http://www.haskell.org/mailman/listinfo/web-devel
_______________________________________________ web-devel mailing list web-devel@haskell.org http://www.haskell.org/mailman/listinfo/web-devel
-- -barkmadley sent from an internet enabled device
-- -barkmadley sent from an internet enabled device
-- -barkmadley sent from an internet enabled device

Oh, you weren't joking, that really is a small patch. I should have looked
before writing this email. OK, it's using the inner block approach. I think
I'm OK including that if we rename it to $with, e.g.:
$with x <- foo bar
#{x}
Michael
On Fri, Apr 8, 2011 at 1:05 PM, Michael Snoyman
On Fri, Apr 8, 2011 at 2:47 AM, Mark Bradley
wrote: A few points: 1) The cost is twofold: making Hamlet more complex from a user
On Thu, Apr 7, 2011 at 11:22 PM, Michael Snoyman
wrote: perspective, and making the codebase more complex. I'm not a fan of either, unless it's really justified. 2) I'm not really certain how your example below works as far as disambiguating Maybe versus [] (i.e., $maybe versus $forall), but if we're willing to go in this direction, you already have $let for free: $forall foo <- foos $forall foobar <- return $ bar foo #{foobar}
I was really going out there with my suggestions and examples. The real benefit of a unified approach is that you can extend it to apply to your custom container types. Making it pretty similar to foldable but with an default behaviour when the data structure is empty.
Actually, forgetting the rest of the discussion here, I think extending $forall to work on any Foldable is a great idea. Any objections?
Also if you already have let for free using forall and return, why not make a sugared version that compiles down to that?
I haven't looked at your patch yet (thank you btw), but my concern is that introducing $let, the same way it's used in Haskell, introduces scoping issues that we don't otherwise have. $forall and $maybe already add a significant complexity to deal with the bound variable names, but at least it's bound for only the inner block. With $let, we would want it to be bound for the remainder of the block most likely. So we'd have two choices:
* Implement a whole bunch of complexity defining and implementing new scoping rules. * Have totally different semantics from Haskell.
I'm not sure which approach your patch took. But maybe the problem was with my choice of name ($let); $with would likely make more sense for the inner block approach. But even so, I'm still concerned that this is complexity without enough reward.
Here, return would be for the [] instance of Monad. We could also use $maybe, using the Maybe instance of Monad. Michael
On Thu, Apr 7, 2011 at 3:46 PM, Mark Bradley
wrote: On Thu, Apr 7, 2011 at 10:34 PM, Mark Bradley
wrote: On Thu, Apr 7, 2011 at 7:51 PM, Max Cantor
put me in the opposed category.
You can just as easily put: let formId rs = fromMaybe "" $ lookup $...
in the haskell function that loads the hamlet file then you just have to put #{formId rs}
in the hamlet. I think adding syntax should be done only when very necessary. seems like a very small win here at a big cost.
Where is the cost? Most of the effort would be just glueing together some pieces of existing code. Given that there are already two places where hamlet does variable binding, adding a third will not hurt it, or perhaps a single more expressive form of variable binding is required. Something like monadic bind (>>=) where you can bind non-monadic values using the identity monad.
An example:
$bind row <- rs $bind formId <- Identity $ fromMaybe "" $ IntMap.lookup $ getInt "form_id" row <td>#{formId counties} <td>#{formId customers}
It could also be possible to do else cases where it didn't bind:
-- list bind $bind row <- rs -- identity bind $bind formId <- Identity $ fromMaybe "" $ IntMap.lookup $ getInt "form_id" row <td>#{formId counties} <td>#{formId customers} -- maybe bind $bind someValue <- someMaybeValue <div>content -- maybe value was Nothing $nobind <div>other content -- not possible with identity bind possible place for error/warning $nobind <div>This should not happen!
-- empty list $nobind <div>i left my content in my other pants
yes, if you have a situation where many handlers are calling the
same
hamlet file, there might be some duplication, but then you can always raise the formId function to a top-level function.
max
On Apr 7, 2011, at 5:15 PM, Michael Snoyman wrote:
> I've been very hesitant about adding more features to Hamlet, > especially ones that are already implemented in Haskell. That's been my > reasoning for avoiding any kind of variable definitions until now. However, > this does seem like a compelling use case. > > I don't think it would make sense to limit it to foralls: it makes as > much sense in maybes, and I think it would be confusing if it only applied > in some cases. As for syntax, how about: > > $forall row <- rs > $let formId = fromMaybe "" $ IntMap.lookup $ getInt "form_id" row > ... > > I'm not 100% sold on this yet, what does everyone else think? > > One last note: I'm probably going to be announcing a feature freeze on > Yesod 0.8 *very* soon, and making a beta release to Yackage so that
> can test. If you have any last-minute input, now's the time. I'm
wrote: people planning on
> giving the beta test period about a week, and then releasing to Hackage. > > Michael > > On Thu, Apr 7, 2011 at 2:57 AM,
wrote: > I noticed a pattern that in hamlet $forall i often retrieve the same > value > from a map, Sometimes 3,4 times. > > $forall row <- rs > <td>#{getStr > "form_name" > row} > <td>#{getStr "docname" row} > ... > <td>#{fromMaybe "" (IntMap.lookup (getInt "form_id" row) > counties)} > <td>#{fromMaybe "" (IntMap.lookup (getInt "form_id" row) > customers)} > > Would it be possible to allow let statement in forall for often used > values ? > > Regards, > Vagif Verdi > > _______________________________________________ > web-devel mailing list > web-devel@haskell.org > http://www.haskell.org/mailman/listinfo/web-devel > > _______________________________________________ > web-devel mailing list > web-devel@haskell.org > http://www.haskell.org/mailman/listinfo/web-devel _______________________________________________ web-devel mailing list web-devel@haskell.org http://www.haskell.org/mailman/listinfo/web-devel
-- -barkmadley sent from an internet enabled device
-- -barkmadley sent from an internet enabled device
-- -barkmadley sent from an internet enabled device

your latest change makes my original patch not work. I updated the
pull request to handle this and deal with the foldable forall problem
that arises from piggy backing on the LineForall construct. It now
uses the LineMaybe to the same effect.
On Fri, Apr 8, 2011 at 8:08 PM, Michael Snoyman
Oh, you weren't joking, that really is a small patch. I should have looked before writing this email. OK, it's using the inner block approach. I think I'm OK including that if we rename it to $with, e.g.: $with x <- foo bar #{x} Michael
On Fri, Apr 8, 2011 at 1:05 PM, Michael Snoyman
wrote: On Fri, Apr 8, 2011 at 2:47 AM, Mark Bradley
wrote: On Thu, Apr 7, 2011 at 11:22 PM, Michael Snoyman
wrote: A few points: 1) The cost is twofold: making Hamlet more complex from a user perspective, and making the codebase more complex. I'm not a fan of either, unless it's really justified. 2) I'm not really certain how your example below works as far as disambiguating Maybe versus [] (i.e., $maybe versus $forall), but if we're willing to go in this direction, you already have $let for free: $forall foo <- foos $forall foobar <- return $ bar foo #{foobar}
I was really going out there with my suggestions and examples. The real benefit of a unified approach is that you can extend it to apply to your custom container types. Making it pretty similar to foldable but with an default behaviour when the data structure is empty.
Actually, forgetting the rest of the discussion here, I think extending $forall to work on any Foldable is a great idea. Any objections?
Also if you already have let for free using forall and return, why not make a sugared version that compiles down to that?
I haven't looked at your patch yet (thank you btw), but my concern is that introducing $let, the same way it's used in Haskell, introduces scoping issues that we don't otherwise have. $forall and $maybe already add a significant complexity to deal with the bound variable names, but at least it's bound for only the inner block. With $let, we would want it to be bound for the remainder of the block most likely. So we'd have two choices: * Implement a whole bunch of complexity defining and implementing new scoping rules. * Have totally different semantics from Haskell. I'm not sure which approach your patch took. But maybe the problem was with my choice of name ($let); $with would likely make more sense for the inner block approach. But even so, I'm still concerned that this is complexity without enough reward.
Here, return would be for the [] instance of Monad. We could also use $maybe, using the Maybe instance of Monad. Michael
On Thu, Apr 7, 2011 at 3:46 PM, Mark Bradley
wrote: On Thu, Apr 7, 2011 at 10:34 PM, Mark Bradley
wrote: On Thu, Apr 7, 2011 at 7:51 PM, Max Cantor
wrote: > put me in the opposed category. > > You can just as easily put: > let formId rs = fromMaybe "" $ lookup $... > > in the haskell function that loads the hamlet file then you just > have > to put > #{formId rs} > > in the hamlet. I think adding syntax should be done only when very > necessary. seems like a very small win here at a big cost. Where is the cost? Most of the effort would be just glueing together some pieces of existing code. Given that there are already two places where hamlet does variable binding, adding a third will not hurt it, or perhaps a single more expressive form of variable binding is required. Something like monadic bind (>>=) where you can bind non-monadic values using the identity monad.
An example:
$bind row <- rs $bind formId <- Identity $ fromMaybe "" $ IntMap.lookup $ getInt "form_id" row <td>#{formId counties} <td>#{formId customers}
It could also be possible to do else cases where it didn't bind:
-- list bind $bind row <- rs -- identity bind $bind formId <- Identity $ fromMaybe "" $ IntMap.lookup $ getInt "form_id" row <td>#{formId counties} <td>#{formId customers} -- maybe bind $bind someValue <- someMaybeValue <div>content -- maybe value was Nothing $nobind <div>other content -- not possible with identity bind possible place for error/warning $nobind <div>This should not happen!
-- empty list $nobind <div>i left my content in my other pants
> > yes, if you have a situation where many handlers are calling the > same > hamlet file, there might be some duplication, but then you can > always raise > the formId function to a top-level function. > > max > > On Apr 7, 2011, at 5:15 PM, Michael Snoyman wrote: > >> I've been very hesitant about adding more features to Hamlet, >> especially ones that are already implemented in Haskell. That's >> been my >> reasoning for avoiding any kind of variable definitions until now. >> However, >> this does seem like a compelling use case. >> >> I don't think it would make sense to limit it to foralls: it makes >> as >> much sense in maybes, and I think it would be confusing if it only >> applied >> in some cases. As for syntax, how about: >> >> $forall row <- rs >> $let formId = fromMaybe "" $ IntMap.lookup $ getInt "form_id" >> row >> ... >> >> I'm not 100% sold on this yet, what does everyone else think? >> >> One last note: I'm probably going to be announcing a feature >> freeze on >> Yesod 0.8 *very* soon, and making a beta release to Yackage so >> that people >> can test. If you have any last-minute input, now's the time. I'm >> planning on >> giving the beta test period about a week, and then releasing to >> Hackage. >> >> Michael >> >> On Thu, Apr 7, 2011 at 2:57 AM,
wrote: >> I noticed a pattern that in hamlet $forall i often retrieve the >> same >> value >> from a map, Sometimes 3,4 times. >> >> $forall row <- rs >> <td>#{getStr >> "form_name" >> row} >> <td>#{getStr "docname" row} >> ... >> <td>#{fromMaybe "" (IntMap.lookup (getInt "form_id" >> row) >> counties)} >> <td>#{fromMaybe "" (IntMap.lookup (getInt "form_id" >> row) >> customers)} >> >> Would it be possible to allow let statement in forall for often >> used >> values ? >> >> Regards, >> Vagif Verdi >> >> _______________________________________________ >> web-devel mailing list >> web-devel@haskell.org >> http://www.haskell.org/mailman/listinfo/web-devel >> >> _______________________________________________ >> web-devel mailing list >> web-devel@haskell.org >> http://www.haskell.org/mailman/listinfo/web-devel > > > _______________________________________________ > web-devel mailing list > web-devel@haskell.org > http://www.haskell.org/mailman/listinfo/web-devel > -- -barkmadley sent from an internet enabled device
-- -barkmadley sent from an internet enabled device
-- -barkmadley sent from an internet enabled device
-- -barkmadley sent from an internet enabled device

Hi Mark,
Do you have an opinion on the naming, i.e. with versus let? Does anyone
else?
Michael
On Fri, Apr 8, 2011 at 4:35 PM, Mark Bradley
your latest change makes my original patch not work. I updated the pull request to handle this and deal with the foldable forall problem that arises from piggy backing on the LineForall construct. It now uses the LineMaybe to the same effect.
Oh, you weren't joking, that really is a small patch. I should have looked before writing this email. OK, it's using the inner block approach. I
I'm OK including that if we rename it to $with, e.g.: $with x <- foo bar #{x} Michael
On Fri, Apr 8, 2011 at 1:05 PM, Michael Snoyman
wrote: On Fri, Apr 8, 2011 at 2:47 AM, Mark Bradley
wrote:
On Thu, Apr 7, 2011 at 11:22 PM, Michael Snoyman
wrote: A few points: 1) The cost is twofold: making Hamlet more complex from a user perspective, and making the codebase more complex. I'm not a fan of either, unless it's really justified. 2) I'm not really certain how your example below works as far as disambiguating Maybe versus [] (i.e., $maybe versus $forall), but if we're willing to go in this direction, you already have $let for free: $forall foo <- foos $forall foobar <- return $ bar foo #{foobar}
I was really going out there with my suggestions and examples. The real benefit of a unified approach is that you can extend it to apply to your custom container types. Making it pretty similar to foldable but with an default behaviour when the data structure is empty.
Actually, forgetting the rest of the discussion here, I think extending $forall to work on any Foldable is a great idea. Any objections?
Also if you already have let for free using forall and return, why not make a sugared version that compiles down to that?
I haven't looked at your patch yet (thank you btw), but my concern is
introducing $let, the same way it's used in Haskell, introduces scoping issues that we don't otherwise have. $forall and $maybe already add a significant complexity to deal with the bound variable names, but at least it's bound for only the inner block. With $let, we would want it to be bound for the remainder of the block most likely. So we'd have two choices: * Implement a whole bunch of complexity defining and implementing new scoping rules. * Have totally different semantics from Haskell. I'm not sure which approach your patch took. But maybe the problem was with my choice of name ($let); $with would likely make more sense for
On Fri, Apr 8, 2011 at 8:08 PM, Michael Snoyman
wrote: think that the inner block approach. But even so, I'm still concerned that this is complexity without enough reward.
Here, return would be for the [] instance of Monad. We could also use $maybe, using the Maybe instance of Monad. Michael
On Thu, Apr 7, 2011 at 3:46 PM, Mark Bradley
wrote: On Thu, Apr 7, 2011 at 10:34 PM, Mark Bradley
wrote: > On Thu, Apr 7, 2011 at 7:51 PM, Max Cantor
> wrote: >> put me in the opposed category. >> >> You can just as easily put: >> let formId rs = fromMaybe "" $ lookup $... >> >> in the haskell function that loads the hamlet file then you just >> have >> to put >> #{formId rs} >> >> in the hamlet. I think adding syntax should be done only when very >> necessary. seems like a very small win here at a big cost. > > Where is the cost? Most of the effort would be just glueing together > some pieces of existing code. Given that there are already two > places > where hamlet does variable binding, adding a third will not hurt it, > or perhaps a single more expressive form of variable binding is > required. Something like monadic bind (>>=) where you can bind > non-monadic values using the identity monad. An example:
$bind row <- rs $bind formId <- Identity $ fromMaybe "" $ IntMap.lookup $ getInt "form_id" row <td>#{formId counties} <td>#{formId customers}
It could also be possible to do else cases where it didn't bind:
-- list bind $bind row <- rs -- identity bind $bind formId <- Identity $ fromMaybe "" $ IntMap.lookup $ getInt "form_id" row <td>#{formId counties} <td>#{formId customers} -- maybe bind $bind someValue <- someMaybeValue <div>content -- maybe value was Nothing $nobind <div>other content -- not possible with identity bind possible place for error/warning $nobind <div>This should not happen!
-- empty list $nobind <div>i left my content in my other pants
> >> >> yes, if you have a situation where many handlers are calling the >> same >> hamlet file, there might be some duplication, but then you can >> always raise >> the formId function to a top-level function. >> >> max >> >> On Apr 7, 2011, at 5:15 PM, Michael Snoyman wrote: >> >>> I've been very hesitant about adding more features to Hamlet, >>> especially ones that are already implemented in Haskell. That's >>> been my >>> reasoning for avoiding any kind of variable definitions until now. >>> However, >>> this does seem like a compelling use case. >>> >>> I don't think it would make sense to limit it to foralls: it makes >>> as >>> much sense in maybes, and I think it would be confusing if it only >>> applied >>> in some cases. As for syntax, how about: >>> >>> $forall row <- rs >>> $let formId = fromMaybe "" $ IntMap.lookup $ getInt "form_id" >>> row >>> ... >>> >>> I'm not 100% sold on this yet, what does everyone else think? >>> >>> One last note: I'm probably going to be announcing a feature >>> freeze on >>> Yesod 0.8 *very* soon, and making a beta release to Yackage so >>> that people >>> can test. If you have any last-minute input, now's the time. I'm >>> planning on >>> giving the beta test period about a week, and then releasing to >>> Hackage. >>> >>> Michael >>> >>> On Thu, Apr 7, 2011 at 2:57 AM,
wrote: >>> I noticed a pattern that in hamlet $forall i often retrieve the >>> same >>> value >>> from a map, Sometimes 3,4 times. >>> >>> $forall row <- rs >>> <td>#{getStr >>> "form_name" >>> row} >>> <td>#{getStr "docname" row} >>> ... >>> <td>#{fromMaybe "" (IntMap.lookup (getInt "form_id" >>> row) >>> counties)} >>> <td>#{fromMaybe "" (IntMap.lookup (getInt "form_id" >>> row) >>> customers)} >>> >>> Would it be possible to allow let statement in forall for often >>> used >>> values ? >>> >>> Regards, >>> Vagif Verdi >>> >>> _______________________________________________ >>> web-devel mailing list >>> web-devel@haskell.org >>> http://www.haskell.org/mailman/listinfo/web-devel >>> >>> _______________________________________________ >>> web-devel mailing list >>> web-devel@haskell.org >>> http://www.haskell.org/mailman/listinfo/web-devel >> >> >> _______________________________________________ >> web-devel mailing list >> web-devel@haskell.org >> http://www.haskell.org/mailman/listinfo/web-devel >> > > > > -- > -barkmadley > sent from an internet enabled device > -- -barkmadley sent from an internet enabled device
-- -barkmadley sent from an internet enabled device
-- -barkmadley sent from an internet enabled device

$with definitely differentiates it from the way that haskell does let
binding and even makes it more obvious about the scoping (with
bindings in languages like python/javascript work this way), even
hinting that it doesn't to pattern matching. I'm in favour.
If we were to implement a $let it would probably have to work on the
current scope otherwise it would confuse, and allow for mutual
recursion perhaps.
On Fri, Apr 8, 2011 at 11:40 PM, Michael Snoyman
Hi Mark, Do you have an opinion on the naming, i.e. with versus let? Does anyone else? Michael
On Fri, Apr 8, 2011 at 4:35 PM, Mark Bradley
wrote: your latest change makes my original patch not work. I updated the pull request to handle this and deal with the foldable forall problem that arises from piggy backing on the LineForall construct. It now uses the LineMaybe to the same effect.
On Fri, Apr 8, 2011 at 8:08 PM, Michael Snoyman
wrote: Oh, you weren't joking, that really is a small patch. I should have looked before writing this email. OK, it's using the inner block approach. I think I'm OK including that if we rename it to $with, e.g.: $with x <- foo bar #{x} Michael
On Fri, Apr 8, 2011 at 1:05 PM, Michael Snoyman
wrote: On Fri, Apr 8, 2011 at 2:47 AM, Mark Bradley
wrote: On Thu, Apr 7, 2011 at 11:22 PM, Michael Snoyman
wrote: A few points: 1) The cost is twofold: making Hamlet more complex from a user perspective, and making the codebase more complex. I'm not a fan of either, unless it's really justified. 2) I'm not really certain how your example below works as far as disambiguating Maybe versus [] (i.e., $maybe versus $forall), but if we're willing to go in this direction, you already have $let for free: $forall foo <- foos $forall foobar <- return $ bar foo #{foobar}
I was really going out there with my suggestions and examples. The real benefit of a unified approach is that you can extend it to apply to your custom container types. Making it pretty similar to foldable but with an default behaviour when the data structure is empty.
Actually, forgetting the rest of the discussion here, I think extending $forall to work on any Foldable is a great idea. Any objections?
Also if you already have let for free using forall and return, why not make a sugared version that compiles down to that?
I haven't looked at your patch yet (thank you btw), but my concern is that introducing $let, the same way it's used in Haskell, introduces scoping issues that we don't otherwise have. $forall and $maybe already add a significant complexity to deal with the bound variable names, but at least it's bound for only the inner block. With $let, we would want it to be bound for the remainder of the block most likely. So we'd have two choices: * Implement a whole bunch of complexity defining and implementing new scoping rules. * Have totally different semantics from Haskell. I'm not sure which approach your patch took. But maybe the problem was with my choice of name ($let); $with would likely make more sense for the inner block approach. But even so, I'm still concerned that this is complexity without enough reward.
Here, return would be for the [] instance of Monad. We could also use $maybe, using the Maybe instance of Monad. Michael
On Thu, Apr 7, 2011 at 3:46 PM, Mark Bradley
wrote: > > On Thu, Apr 7, 2011 at 10:34 PM, Mark Bradley > > wrote: > > On Thu, Apr 7, 2011 at 7:51 PM, Max Cantor > > wrote: > >> put me in the opposed category. > >> > >> You can just as easily put: > >> let formId rs = fromMaybe "" $ lookup $... > >> > >> in the haskell function that loads the hamlet file then you just > >> have > >> to put > >> #{formId rs} > >> > >> in the hamlet. I think adding syntax should be done only when > >> very > >> necessary. seems like a very small win here at a big cost. > > > > Where is the cost? Most of the effort would be just glueing > > together > > some pieces of existing code. Given that there are already two > > places > > where hamlet does variable binding, adding a third will not hurt > > it, > > or perhaps a single more expressive form of variable binding is > > required. Something like monadic bind (>>=) where you can bind > > non-monadic values using the identity monad. > > An example: > > $bind row <- rs > $bind formId <- Identity $ fromMaybe "" $ IntMap.lookup $ getInt > "form_id" row > <td>#{formId counties} > <td>#{formId customers} > > It could also be possible to do else cases where it didn't bind: > > -- list bind > $bind row <- rs > -- identity bind > $bind formId <- Identity $ fromMaybe "" $ IntMap.lookup $ getInt > "form_id" row > <td>#{formId counties} > <td>#{formId customers} > -- maybe bind > $bind someValue <- someMaybeValue > <div>content > -- maybe value was Nothing > $nobind > <div>other content > -- not possible with identity bind possible place for > error/warning > $nobind > <div>This should not happen! > > -- empty list > $nobind > <div>i left my content in my other pants > > > > > > >> > >> yes, if you have a situation where many handlers are calling the > >> same > >> hamlet file, there might be some duplication, but then you can > >> always raise > >> the formId function to a top-level function. > >> > >> max > >> > >> On Apr 7, 2011, at 5:15 PM, Michael Snoyman wrote: > >> > >>> I've been very hesitant about adding more features to Hamlet, > >>> especially ones that are already implemented in Haskell. That's > >>> been my > >>> reasoning for avoiding any kind of variable definitions until > >>> now. > >>> However, > >>> this does seem like a compelling use case. > >>> > >>> I don't think it would make sense to limit it to foralls: it > >>> makes > >>> as > >>> much sense in maybes, and I think it would be confusing if it > >>> only > >>> applied > >>> in some cases. As for syntax, how about: > >>> > >>> $forall row <- rs > >>> $let formId = fromMaybe "" $ IntMap.lookup $ getInt > >>> "form_id" > >>> row > >>> ... > >>> > >>> I'm not 100% sold on this yet, what does everyone else think? > >>> > >>> One last note: I'm probably going to be announcing a feature > >>> freeze on > >>> Yesod 0.8 *very* soon, and making a beta release to Yackage so > >>> that people > >>> can test. If you have any last-minute input, now's the time. > >>> I'm > >>> planning on > >>> giving the beta test period about a week, and then releasing to > >>> Hackage. > >>> > >>> Michael > >>> > >>> On Thu, Apr 7, 2011 at 2:57 AM, wrote: > >>> I noticed a pattern that in hamlet $forall i often retrieve the > >>> same > >>> value > >>> from a map, Sometimes 3,4 times. > >>> > >>> $forall row <- rs > >>> <td>#{getStr > >>> "form_name" > >>> row} > >>> <td>#{getStr "docname" row} > >>> ... > >>> <td>#{fromMaybe "" (IntMap.lookup (getInt "form_id" > >>> row) > >>> counties)} > >>> <td>#{fromMaybe "" (IntMap.lookup (getInt "form_id" > >>> row) > >>> customers)} > >>> > >>> Would it be possible to allow let statement in forall for often > >>> used > >>> values ? > >>> > >>> Regards, > >>> Vagif Verdi > >>> > >>> _______________________________________________ > >>> web-devel mailing list > >>> web-devel@haskell.org > >>> http://www.haskell.org/mailman/listinfo/web-devel > >>> > >>> _______________________________________________ > >>> web-devel mailing list > >>> web-devel@haskell.org > >>> http://www.haskell.org/mailman/listinfo/web-devel > >> > >> > >> _______________________________________________ > >> web-devel mailing list > >> web-devel@haskell.org > >> http://www.haskell.org/mailman/listinfo/web-devel > >> > > > > > > > > -- > > -barkmadley > > sent from an internet enabled device > > > > > > -- > -barkmadley > sent from an internet enabled device -- -barkmadley sent from an internet enabled device
-- -barkmadley sent from an internet enabled device
-- -barkmadley sent from an internet enabled device

I agree with your comments about $let, which is why I'm reluctant to do so.
If no one has any objections, I'll pull your patch and rename to with. Also,
for consistency, I'll use <- instead of =. In other words:
$width foo <- bar
#{foo}
Michael
On Fri, Apr 8, 2011 at 4:45 PM, Mark Bradley
$with definitely differentiates it from the way that haskell does let binding and even makes it more obvious about the scoping (with bindings in languages like python/javascript work this way), even hinting that it doesn't to pattern matching. I'm in favour.
If we were to implement a $let it would probably have to work on the current scope otherwise it would confuse, and allow for mutual recursion perhaps.
Hi Mark, Do you have an opinion on the naming, i.e. with versus let? Does anyone else? Michael
On Fri, Apr 8, 2011 at 4:35 PM, Mark Bradley
wrote: your latest change makes my original patch not work. I updated the pull request to handle this and deal with the foldable forall problem that arises from piggy backing on the LineForall construct. It now uses the LineMaybe to the same effect.
On Fri, Apr 8, 2011 at 8:08 PM, Michael Snoyman
wrote: Oh, you weren't joking, that really is a small patch. I should have looked before writing this email. OK, it's using the inner block approach. I think I'm OK including that if we rename it to $with, e.g.: $with x <- foo bar #{x} Michael
On Fri, Apr 8, 2011 at 1:05 PM, Michael Snoyman
wrote: On Fri, Apr 8, 2011 at 2:47 AM, Mark Bradley
wrote: On Thu, Apr 7, 2011 at 11:22 PM, Michael Snoyman <
michael@snoyman.com>
wrote: > A few points: > 1) The cost is twofold: making Hamlet more complex from a user > perspective, > and making the codebase more complex. I'm not a fan of either, > unless > it's > really justified. > 2) I'm not really certain how your example below works as far as > disambiguating Maybe versus [] (i.e., $maybe versus $forall), but if > we're > willing to go in this direction, you already have $let for free: > $forall foo <- foos > $forall foobar <- return $ bar foo > #{foobar}
I was really going out there with my suggestions and examples. The real benefit of a unified approach is that you can extend it to apply to your custom container types. Making it pretty similar to foldable but with an default behaviour when the data structure is empty.
Actually, forgetting the rest of the discussion here, I think extending $forall to work on any Foldable is a great idea. Any objections?
Also if you already have let for free using forall and return, why
not
make a sugared version that compiles down to that?
I haven't looked at your patch yet (thank you btw), but my concern is that introducing $let, the same way it's used in Haskell, introduces scoping issues that we don't otherwise have. $forall and $maybe already add a significant complexity to deal with the bound variable names, but at least it's bound for only the inner block. With $let, we would want it to be bound for the remainder of the block most likely. So we'd have two choices: * Implement a whole bunch of complexity defining and implementing new scoping rules. * Have totally different semantics from Haskell. I'm not sure which approach your patch took. But maybe the problem was with my choice of name ($let); $with would likely make more sense for the inner block approach. But even so, I'm still concerned that this is complexity without enough reward.
> Here, return would be for the [] instance of Monad. We could also > use > $maybe, using the Maybe instance of Monad. > Michael > > On Thu, Apr 7, 2011 at 3:46 PM, Mark Bradley <
barkmadley@gmail.com>
> wrote: >> >> On Thu, Apr 7, 2011 at 10:34 PM, Mark Bradley >>
>> wrote: >> > On Thu, Apr 7, 2011 at 7:51 PM, Max Cantor >> > wrote: >> >> put me in the opposed category. >> >> >> >> You can just as easily put: >> >> let formId rs = fromMaybe "" $ lookup $... >> >> >> >> in the haskell function that loads the hamlet file then you just >> >> have >> >> to put >> >> #{formId rs} >> >> >> >> in the hamlet. I think adding syntax should be done only when >> >> very >> >> necessary. seems like a very small win here at a big cost. >> > >> > Where is the cost? Most of the effort would be just glueing >> > together >> > some pieces of existing code. Given that there are already two >> > places >> > where hamlet does variable binding, adding a third will not hurt >> > it, >> > or perhaps a single more expressive form of variable binding is >> > required. Something like monadic bind (>>=) where you can bind >> > non-monadic values using the identity monad. >> >> An example: >> >> $bind row <- rs >> $bind formId <- Identity $ fromMaybe "" $ IntMap.lookup $ getInt >> "form_id" row >> <td>#{formId counties} >> <td>#{formId customers} >> >> It could also be possible to do else cases where it didn't bind: >> >> -- list bind >> $bind row <- rs >> -- identity bind >> $bind formId <- Identity $ fromMaybe "" $ IntMap.lookup $ getInt >> "form_id" row >> <td>#{formId counties} >> <td>#{formId customers} >> -- maybe bind >> $bind someValue <- someMaybeValue >> <div>content >> -- maybe value was Nothing >> $nobind >> <div>other content >> -- not possible with identity bind possible place for >> error/warning >> $nobind >> <div>This should not happen! >> >> -- empty list >> $nobind >> <div>i left my content in my other pants >> >> >> >> > >> >> >> >> yes, if you have a situation where many handlers are calling
>> >> same >> >> hamlet file, there might be some duplication, but then you can >> >> always raise >> >> the formId function to a top-level function. >> >> >> >> max >> >> >> >> On Apr 7, 2011, at 5:15 PM, Michael Snoyman wrote: >> >> >> >>> I've been very hesitant about adding more features to Hamlet, >> >>> especially ones that are already implemented in Haskell. That's >> >>> been my >> >>> reasoning for avoiding any kind of variable definitions until >> >>> now. >> >>> However, >> >>> this does seem like a compelling use case. >> >>> >> >>> I don't think it would make sense to limit it to foralls: it >> >>> makes >> >>> as >> >>> much sense in maybes, and I think it would be confusing if it >> >>> only >> >>> applied >> >>> in some cases. As for syntax, how about: >> >>> >> >>> $forall row <- rs >> >>> $let formId = fromMaybe "" $ IntMap.lookup $ getInt >> >>> "form_id" >> >>> row >> >>> ... >> >>> >> >>> I'm not 100% sold on this yet, what does everyone else think? >> >>> >> >>> One last note: I'm probably going to be announcing a feature >> >>> freeze on >> >>> Yesod 0.8 *very* soon, and making a beta release to Yackage so >> >>> that people >> >>> can test. If you have any last-minute input, now's the time. >> >>> I'm >> >>> planning on >> >>> giving the beta test period about a week, and then releasing to >> >>> Hackage. >> >>> >> >>> Michael >> >>> >> >>> On Thu, Apr 7, 2011 at 2:57 AM,
wrote: >> >>> I noticed a pattern that in hamlet $forall i often retrieve On Fri, Apr 8, 2011 at 11:40 PM, Michael Snoyman
wrote: the the >> >>> same >> >>> value >> >>> from a map, Sometimes 3,4 times. >> >>> >> >>> $forall row <- rs >> >>> <td>#{getStr >> >>> "form_name" >> >>> row} >> >>> <td>#{getStr "docname" row} >> >>> ... >> >>> <td>#{fromMaybe "" (IntMap.lookup (getInt "form_id" >> >>> row) >> >>> counties)} >> >>> <td>#{fromMaybe "" (IntMap.lookup (getInt "form_id" >> >>> row) >> >>> customers)} >> >>> >> >>> Would it be possible to allow let statement in forall for often >> >>> used >> >>> values ? >> >>> >> >>> Regards, >> >>> Vagif Verdi >> >>> >> >>> _______________________________________________ >> >>> web-devel mailing list >> >>> web-devel@haskell.org >> >>> http://www.haskell.org/mailman/listinfo/web-devel >> >>> >> >>> _______________________________________________ >> >>> web-devel mailing list >> >>> web-devel@haskell.org >> >>> http://www.haskell.org/mailman/listinfo/web-devel >> >> >> >> >> >> _______________________________________________ >> >> web-devel mailing list >> >> web-devel@haskell.org >> >> http://www.haskell.org/mailman/listinfo/web-devel >> >> >> > >> > >> > >> > -- >> > -barkmadley >> > sent from an internet enabled device >> > >> >> >> >> -- >> -barkmadley >> sent from an internet enabled device > >
-- -barkmadley sent from an internet enabled device
-- -barkmadley sent from an internet enabled device
-- -barkmadley sent from an internet enabled device

check the patch again
On Fri, Apr 8, 2011 at 11:47 PM, Michael Snoyman
I agree with your comments about $let, which is why I'm reluctant to do so. If no one has any objections, I'll pull your patch and rename to with. Also, for consistency, I'll use <- instead of =. In other words: $width foo <- bar #{foo} Michael
On Fri, Apr 8, 2011 at 4:45 PM, Mark Bradley
wrote: $with definitely differentiates it from the way that haskell does let binding and even makes it more obvious about the scoping (with bindings in languages like python/javascript work this way), even hinting that it doesn't to pattern matching. I'm in favour.
If we were to implement a $let it would probably have to work on the current scope otherwise it would confuse, and allow for mutual recursion perhaps.
On Fri, Apr 8, 2011 at 11:40 PM, Michael Snoyman
wrote: Hi Mark, Do you have an opinion on the naming, i.e. with versus let? Does anyone else? Michael
On Fri, Apr 8, 2011 at 4:35 PM, Mark Bradley
wrote: your latest change makes my original patch not work. I updated the pull request to handle this and deal with the foldable forall problem that arises from piggy backing on the LineForall construct. It now uses the LineMaybe to the same effect.
On Fri, Apr 8, 2011 at 8:08 PM, Michael Snoyman
wrote: Oh, you weren't joking, that really is a small patch. I should have looked before writing this email. OK, it's using the inner block approach. I think I'm OK including that if we rename it to $with, e.g.: $with x <- foo bar #{x} Michael
On Fri, Apr 8, 2011 at 1:05 PM, Michael Snoyman
wrote: On Fri, Apr 8, 2011 at 2:47 AM, Mark Bradley
wrote: > > On Thu, Apr 7, 2011 at 11:22 PM, Michael Snoyman > > wrote: > > A few points: > > 1) The cost is twofold: making Hamlet more complex from a user > > perspective, > > and making the codebase more complex. I'm not a fan of either, > > unless > > it's > > really justified. > > 2) I'm not really certain how your example below works as far as > > disambiguating Maybe versus [] (i.e., $maybe versus $forall), but > > if > > we're > > willing to go in this direction, you already have $let for free: > > $forall foo <- foos > > $forall foobar <- return $ bar foo > > #{foobar} > > I was really going out there with my suggestions and examples. The > real benefit of a unified approach is that you can extend it to > apply > to your custom container types. Making it pretty similar to > foldable > but with an default behaviour when the data structure is empty. > Actually, forgetting the rest of the discussion here, I think extending $forall to work on any Foldable is a great idea. Any objections? > > Also if you already have let for free using forall and return, why > not > make a sugared version that compiles down to that? > I haven't looked at your patch yet (thank you btw), but my concern is that introducing $let, the same way it's used in Haskell, introduces scoping issues that we don't otherwise have. $forall and $maybe already add a significant complexity to deal with the bound variable names, but at least it's bound for only the inner block. With $let, we would want it to be bound for the remainder of the block most likely. So we'd have two choices: * Implement a whole bunch of complexity defining and implementing new scoping rules. * Have totally different semantics from Haskell. I'm not sure which approach your patch took. But maybe the problem was with my choice of name ($let); $with would likely make more sense for the inner block approach. But even so, I'm still concerned that this is complexity without enough reward.
> > > Here, return would be for the [] instance of Monad. We could also > > use > > $maybe, using the Maybe instance of Monad. > > Michael > > > > On Thu, Apr 7, 2011 at 3:46 PM, Mark Bradley > >
> > wrote: > >> > >> On Thu, Apr 7, 2011 at 10:34 PM, Mark Bradley > >> > >> wrote: > >> > On Thu, Apr 7, 2011 at 7:51 PM, Max Cantor > >> > > >> > wrote: > >> >> put me in the opposed category. > >> >> > >> >> You can just as easily put: > >> >> let formId rs = fromMaybe "" $ lookup $... > >> >> > >> >> in the haskell function that loads the hamlet file then you > >> >> just > >> >> have > >> >> to put > >> >> #{formId rs} > >> >> > >> >> in the hamlet. I think adding syntax should be done only > >> >> when > >> >> very > >> >> necessary. seems like a very small win here at a big cost. > >> > > >> > Where is the cost? Most of the effort would be just glueing > >> > together > >> > some pieces of existing code. Given that there are already two > >> > places > >> > where hamlet does variable binding, adding a third will not > >> > hurt > >> > it, > >> > or perhaps a single more expressive form of variable binding > >> > is > >> > required. Something like monadic bind (>>=) where you can bind > >> > non-monadic values using the identity monad. > >> > >> An example: > >> > >> $bind row <- rs > >> $bind formId <- Identity $ fromMaybe "" $ IntMap.lookup $ > >> getInt > >> "form_id" row > >> <td>#{formId counties} > >> <td>#{formId customers} > >> > >> It could also be possible to do else cases where it didn't bind: > >> > >> -- list bind > >> $bind row <- rs > >> -- identity bind > >> $bind formId <- Identity $ fromMaybe "" $ IntMap.lookup $ > >> getInt > >> "form_id" row > >> <td>#{formId counties} > >> <td>#{formId customers} > >> -- maybe bind > >> $bind someValue <- someMaybeValue > >> <div>content > >> -- maybe value was Nothing > >> $nobind > >> <div>other content > >> -- not possible with identity bind possible place for > >> error/warning > >> $nobind > >> <div>This should not happen! > >> > >> -- empty list > >> $nobind > >> <div>i left my content in my other pants > >> > >> > >> > >> > > >> >> > >> >> yes, if you have a situation where many handlers are calling > >> >> the > >> >> same > >> >> hamlet file, there might be some duplication, but then you > >> >> can > >> >> always raise > >> >> the formId function to a top-level function. > >> >> > >> >> max > >> >> > >> >> On Apr 7, 2011, at 5:15 PM, Michael Snoyman wrote: > >> >> > >> >>> I've been very hesitant about adding more features to > >> >>> Hamlet, > >> >>> especially ones that are already implemented in Haskell. > >> >>> That's > >> >>> been my > >> >>> reasoning for avoiding any kind of variable definitions > >> >>> until > >> >>> now. > >> >>> However, > >> >>> this does seem like a compelling use case. > >> >>> > >> >>> I don't think it would make sense to limit it to foralls: it > >> >>> makes > >> >>> as > >> >>> much sense in maybes, and I think it would be confusing if > >> >>> it > >> >>> only > >> >>> applied > >> >>> in some cases. As for syntax, how about: > >> >>> > >> >>> $forall row <- rs > >> >>> $let formId = fromMaybe "" $ IntMap.lookup $ getInt > >> >>> "form_id" > >> >>> row > >> >>> ... > >> >>> > >> >>> I'm not 100% sold on this yet, what does everyone else > >> >>> think? > >> >>> > >> >>> One last note: I'm probably going to be announcing a feature > >> >>> freeze on > >> >>> Yesod 0.8 *very* soon, and making a beta release to Yackage > >> >>> so > >> >>> that people > >> >>> can test. If you have any last-minute input, now's the time. > >> >>> I'm > >> >>> planning on > >> >>> giving the beta test period about a week, and then releasing > >> >>> to > >> >>> Hackage. > >> >>> > >> >>> Michael > >> >>> > >> >>> On Thu, Apr 7, 2011 at 2:57 AM, > >> >>> wrote: > >> >>> I noticed a pattern that in hamlet $forall i often retrieve > >> >>> the > >> >>> same > >> >>> value > >> >>> from a map, Sometimes 3,4 times. > >> >>> > >> >>> $forall row <- rs > >> >>> <td> >> >>> row)}>#{getStr > >> >>> "form_name" > >> >>> row} > >> >>> <td>#{getStr "docname" row} > >> >>> ... > >> >>> <td>#{fromMaybe "" (IntMap.lookup (getInt > >> >>> "form_id" > >> >>> row) > >> >>> counties)} > >> >>> <td>#{fromMaybe "" (IntMap.lookup (getInt > >> >>> "form_id" > >> >>> row) > >> >>> customers)} > >> >>> > >> >>> Would it be possible to allow let statement in forall for > >> >>> often > >> >>> used > >> >>> values ? > >> >>> > >> >>> Regards, > >> >>> Vagif Verdi > >> >>> > >> >>> _______________________________________________ > >> >>> web-devel mailing list > >> >>> web-devel@haskell.org > >> >>> http://www.haskell.org/mailman/listinfo/web-devel > >> >>> > >> >>> _______________________________________________ > >> >>> web-devel mailing list > >> >>> web-devel@haskell.org > >> >>> http://www.haskell.org/mailman/listinfo/web-devel > >> >> > >> >> > >> >> _______________________________________________ > >> >> web-devel mailing list > >> >> web-devel@haskell.org > >> >> http://www.haskell.org/mailman/listinfo/web-devel > >> >> > >> > > >> > > >> > > >> > -- > >> > -barkmadley > >> > sent from an internet enabled device > >> > > >> > >> > >> > >> -- > >> -barkmadley > >> sent from an internet enabled device > > > > > > > > -- > -barkmadley > sent from an internet enabled device -- -barkmadley sent from an internet enabled device
-- -barkmadley sent from an internet enabled device
-- -barkmadley sent from an internet enabled device

Will it be $with foo <- getFoo bar <- getBar or will it be $with foo <- getFoo $with bar <- getBar On Friday, April 08, 2011 06:47:22 AM you wrote:
I agree with your comments about $let, which is why I'm reluctant to do so. If no one has any objections, I'll pull your patch and rename to with. Also, for consistency, I'll use <- instead of =. In other words:
$width foo <- bar #{foo}
Michael
On Fri, Apr 8, 2011 at 4:45 PM, Mark Bradley
wrote: $with definitely differentiates it from the way that haskell does let binding and even makes it more obvious about the scoping (with bindings in languages like python/javascript work this way), even hinting that it doesn't to pattern matching. I'm in favour.
If we were to implement a $let it would probably have to work on the current scope otherwise it would confuse, and allow for mutual recursion perhaps.
On Fri, Apr 8, 2011 at 11:40 PM, Michael Snoyman
wrote:
Hi Mark, Do you have an opinion on the naming, i.e. with versus let? Does anyone else? Michael
On Fri, Apr 8, 2011 at 4:35 PM, Mark Bradley
wrote:
your latest change makes my original patch not work. I updated the pull request to handle this and deal with the foldable forall problem that arises from piggy backing on the LineForall construct. It now uses the LineMaybe to the same effect.
On Fri, Apr 8, 2011 at 8:08 PM, Michael Snoyman
wrote:
Oh, you weren't joking, that really is a small patch. I should have looked before writing this email. OK, it's using the inner block approach. I think I'm OK including that if we rename it to $with, e.g.: $with x <- foo bar
#{x}
Michael
On Fri, Apr 8, 2011 at 1:05 PM, Michael Snoyman
wrote:
On Fri, Apr 8, 2011 at 2:47 AM, Mark Bradley
wrote: > On Thu, Apr 7, 2011 at 11:22 PM, Michael Snoyman <
michael@snoyman.com>
> wrote: > > A few points: > > 1) The cost is twofold: making Hamlet more complex from a user > > perspective, > > and making the codebase more complex. I'm not a fan of either, > > unless > > it's > > really justified. > > 2) I'm not really certain how your example below works as far as > > disambiguating Maybe versus [] (i.e., $maybe versus $forall), > > but
if
> > we're > > willing to go in this direction, you already have $let for free: > > $forall foo <- foos > > > > $forall foobar <- return $ bar foo > > > > #{foobar} > > I was really going out there with my suggestions and examples. > The real benefit of a unified approach is that you can extend it > to
apply
> to your custom container types. Making it pretty similar to
foldable
> but with an default behaviour when the data structure is empty.
Actually, forgetting the rest of the discussion here, I think
extending
$forall to work on any Foldable is a great idea. Any objections?
> Also if you already have let for free using forall and return, why
not
> make a sugared version that compiles down to that?
I haven't looked at your patch yet (thank you btw), but my concern is that introducing $let, the same way it's used in Haskell, introduces
scoping
issues that we don't otherwise have. $forall and $maybe already add a significant complexity to deal with the bound variable names, but at least it's bound for only the inner block. With $let, we would want it to
be
bound for the remainder of the block most likely. So we'd have two choices: * Implement a whole bunch of complexity defining and implementing new scoping rules. * Have totally different semantics from Haskell. I'm not sure which approach your patch took. But maybe the problem
was
with my choice of name ($let); $with would likely make more sense for the inner block approach. But even so, I'm still concerned that this is complexity without enough reward.
> > Here, return would be for the [] instance of Monad. We could > > also use > > $maybe, using the Maybe instance of Monad. > > Michael > > > > On Thu, Apr 7, 2011 at 3:46 PM, Mark Bradley <
barkmadley@gmail.com>
> > wrote: > >> On Thu, Apr 7, 2011 at 10:34 PM, Mark Bradley > >>
> >> > >> wrote: > >> > On Thu, Apr 7, 2011 at 7:51 PM, Max Cantor > >> > >> > > >> > wrote: > >> >> put me in the opposed category. > >> >> > >> >> You can just as easily put: > >> >> let formId rs = fromMaybe "" $ lookup $... > >> >> > >> >> in the haskell function that loads the hamlet file then you just
> >> >> have > >> >> to put > >> >> > >> >> #{formId rs} > >> >> > >> >> in the hamlet. I think adding syntax should be done only > >> >> when very > >> >> necessary. seems like a very small win here at a big cost. > >> > > >> > Where is the cost? Most of the effort would be just glueing > >> > together > >> > some pieces of existing code. Given that there are already > >> > two places > >> > where hamlet does variable binding, adding a third will not
hurt
> >> > it, > >> > or perhaps a single more expressive form of variable binding > >> > is required. Something like monadic bind (>>=) where you can > >> > bind non-monadic values using the identity monad. > >> > >> An example: > >> > >> $bind row <- rs > >> > >> $bind formId <- Identity $ fromMaybe "" $ IntMap.lookup $
getInt
> >> "form_id" row > >> > >> <td>#{formId counties} > >> <td>#{formId customers} > >> > >> It could also be possible to do else cases where it didn't > >> bind: > >> > >> -- list bind > >> $bind row <- rs > >> > >> -- identity bind > >> $bind formId <- Identity $ fromMaybe "" $ IntMap.lookup $
getInt
> >> "form_id" row > >> > >> <td>#{formId counties} > >> <td>#{formId customers} > >> -- maybe bind > >> $bind someValue <- someMaybeValue > >> > >> <div>content > >> > >> -- maybe value was Nothing > >> $nobind > >> > >> <div>other content > >> > >> -- not possible with identity bind possible place for > >> > >> error/warning > >> > >> $nobind > >> > >> <div>This should not happen! > >> > >> -- empty list > >> $nobind > >> > >> <div>i left my content in my other pants > >> > >> >> yes, if you have a situation where many handlers are calling
the
> >> >> same > >> >> hamlet file, there might be some duplication, but then you > >> >> can always raise > >> >> the formId function to a top-level function. > >> >> > >> >> max > >> >> > >> >> On Apr 7, 2011, at 5:15 PM, Michael Snoyman wrote: > >> >>> I've been very hesitant about adding more features to > >> >>> Hamlet, especially ones that are already implemented in > >> >>> Haskell.
That's
> >> >>> been my > >> >>> reasoning for avoiding any kind of variable definitions > >> >>> until now. > >> >>> However, > >> >>> this does seem like a compelling use case. > >> >>> > >> >>> I don't think it would make sense to limit it to foralls: > >> >>> it makes > >> >>> as > >> >>> much sense in maybes, and I think it would be confusing if > >> >>> it only > >> >>> applied > >> >>> in some cases. As for syntax, how about: > >> >>> > >> >>> $forall row <- rs > >> >>> > >> >>> $let formId = fromMaybe "" $ IntMap.lookup $ getInt > >> >>> > >> >>> "form_id" > >> >>> row > >> >>> > >> >>> ... > >> >>> > >> >>> I'm not 100% sold on this yet, what does everyone else > >> >>> think? > >> >>> > >> >>> One last note: I'm probably going to be announcing a > >> >>> feature freeze on > >> >>> Yesod 0.8 *very* soon, and making a beta release to Yackage
so
> >> >>> that people > >> >>> can test. If you have any last-minute input, now's the > >> >>> time. I'm > >> >>> planning on > >> >>> giving the beta test period about a week, and then > >> >>> releasing
to
> >> >>> Hackage. > >> >>> > >> >>> Michael > >> >>> > >> >>> On Thu, Apr 7, 2011 at 2:57 AM,
wrote:
> >> >>> I noticed a pattern that in hamlet $forall i often retrieve
the
> >> >>> same > >> >>> value > >> >>> from a map, Sometimes 3,4 times. > >> >>> > >> >>> $forall row <- rs > >> >>> > >> >>> <td>
row)}>#{getStr
> >> >>> "form_name" > >> >>> row} > >> >>> > >> >>> <td>#{getStr "docname" row} > >> >>> ... > >> >>> <td>#{fromMaybe "" (IntMap.lookup (getInt
"form_id"
> >> >>> row) > >> >>> counties)} > >> >>> > >> >>> <td>#{fromMaybe "" (IntMap.lookup (getInt
"form_id"
> >> >>> row) > >> >>> customers)} > >> >>> > >> >>> Would it be possible to allow let statement in forall for
often
> >> >>> used > >> >>> values ? > >> >>> > >> >>> Regards, > >> >>> Vagif Verdi > >> >>> > >> >>> _______________________________________________ > >> >>> web-devel mailing list > >> >>> web-devel@haskell.org > >> >>> http://www.haskell.org/mailman/listinfo/web-devel > >> >>> > >> >>> _______________________________________________ > >> >>> web-devel mailing list > >> >>> web-devel@haskell.org > >> >>> http://www.haskell.org/mailman/listinfo/web-devel > >> >> > >> >> _______________________________________________ > >> >> web-devel mailing list > >> >> web-devel@haskell.org > >> >> http://www.haskell.org/mailman/listinfo/web-devel > >> > > >> > -- > >> > -barkmadley > >> > sent from an internet enabled device > >> > >> -- > >> -barkmadley > >> sent from an internet enabled device > > -- > -barkmadley > sent from an internet enabled device
-- -barkmadley sent from an internet enabled device
-- -barkmadley sent from an internet enabled device

the proposed patch would be the latter.
On Sat, Apr 9, 2011 at 1:13 AM,
Will it be
$with foo <- getFoo bar <- getBar
or will it be
$with foo <- getFoo $with bar <- getBar
On Friday, April 08, 2011 06:47:22 AM you wrote:
I agree with your comments about $let, which is why I'm reluctant to do so. If no one has any objections, I'll pull your patch and rename to with. Also, for consistency, I'll use <- instead of =. In other words:
$width foo <- bar #{foo}
Michael
On Fri, Apr 8, 2011 at 4:45 PM, Mark Bradley
wrote: $with definitely differentiates it from the way that haskell does let binding and even makes it more obvious about the scoping (with bindings in languages like python/javascript work this way), even hinting that it doesn't to pattern matching. I'm in favour.
If we were to implement a $let it would probably have to work on the current scope otherwise it would confuse, and allow for mutual recursion perhaps.
On Fri, Apr 8, 2011 at 11:40 PM, Michael Snoyman
wrote:
Hi Mark, Do you have an opinion on the naming, i.e. with versus let? Does anyone else? Michael
On Fri, Apr 8, 2011 at 4:35 PM, Mark Bradley
wrote:
your latest change makes my original patch not work. I updated the pull request to handle this and deal with the foldable forall problem that arises from piggy backing on the LineForall construct. It now uses the LineMaybe to the same effect.
On Fri, Apr 8, 2011 at 8:08 PM, Michael Snoyman
wrote:
Oh, you weren't joking, that really is a small patch. I should have looked before writing this email. OK, it's using the inner block approach. I think I'm OK including that if we rename it to $with, e.g.: $with x <- foo bar
#{x}
Michael
On Fri, Apr 8, 2011 at 1:05 PM, Michael Snoyman
wrote: > On Fri, Apr 8, 2011 at 2:47 AM, Mark Bradley
> > wrote: >> On Thu, Apr 7, 2011 at 11:22 PM, Michael Snoyman < michael@snoyman.com>
>> wrote: >> > A few points: >> > 1) The cost is twofold: making Hamlet more complex from a user >> > perspective, >> > and making the codebase more complex. I'm not a fan of either, >> > unless >> > it's >> > really justified. >> > 2) I'm not really certain how your example below works as far as >> > disambiguating Maybe versus [] (i.e., $maybe versus $forall), >> > but
if
>> > we're >> > willing to go in this direction, you already have $let for free: >> > $forall foo <- foos >> > >> > $forall foobar <- return $ bar foo >> > >> > #{foobar} >> >> I was really going out there with my suggestions and examples. >> The real benefit of a unified approach is that you can extend it >> to
apply
>> to your custom container types. Making it pretty similar to
foldable
>> but with an default behaviour when the data structure is empty. > > Actually, forgetting the rest of the discussion here, I think
extending
> $forall to work on any Foldable is a great idea. Any objections? > >> Also if you already have let for free using forall and return, why
not
>> make a sugared version that compiles down to that? > > I haven't looked at your patch yet (thank you btw), but my concern > is that > introducing $let, the same way it's used in Haskell, introduces
scoping
> issues that we don't otherwise have. $forall and $maybe already add > a significant complexity to deal with the bound variable names, > but at least > it's bound for only the inner block. With $let, we would want it to
be
> bound > for the remainder of the block most likely. So we'd have two > choices: * Implement a whole bunch of complexity defining and > implementing new scoping rules. > * Have totally different semantics from Haskell. > I'm not sure which approach your patch took. But maybe the problem
was
> with my choice of name ($let); $with would likely make more sense > for the > inner block approach. But even so, I'm still concerned that this is > complexity without enough reward. > >> > Here, return would be for the [] instance of Monad. We could >> > also use >> > $maybe, using the Maybe instance of Monad. >> > Michael >> > >> > On Thu, Apr 7, 2011 at 3:46 PM, Mark Bradley <
barkmadley@gmail.com>
>> > wrote: >> >> On Thu, Apr 7, 2011 at 10:34 PM, Mark Bradley >> >>
>> >> >> >> wrote: >> >> > On Thu, Apr 7, 2011 at 7:51 PM, Max Cantor >> >> > > >> > >> >> > wrote: >> >> >> put me in the opposed category. >> >> >> >> >> >> You can just as easily put: >> >> >> let formId rs = fromMaybe "" $ lookup $... >> >> >> >> >> >> in the haskell function that loads the hamlet file then you just
>> >> >> have >> >> >> to put >> >> >> >> >> >> #{formId rs} >> >> >> >> >> >> in the hamlet. I think adding syntax should be done only >> >> >> when very >> >> >> necessary. seems like a very small win here at a big cost. >> >> > >> >> > Where is the cost? Most of the effort would be just glueing >> >> > together >> >> > some pieces of existing code. Given that there are already >> >> > two places >> >> > where hamlet does variable binding, adding a third will not
hurt
>> >> > it, >> >> > or perhaps a single more expressive form of variable binding >> >> > is required. Something like monadic bind (>>=) where you can >> >> > bind non-monadic values using the identity monad. >> >> >> >> An example: >> >> >> >> $bind row <- rs >> >> >> >> $bind formId <- Identity $ fromMaybe "" $ IntMap.lookup $
getInt
>> >> "form_id" row >> >> >> >> <td>#{formId counties} >> >> <td>#{formId customers} >> >> >> >> It could also be possible to do else cases where it didn't >> >> bind: >> >> >> >> -- list bind >> >> $bind row <- rs >> >> >> >> -- identity bind >> >> $bind formId <- Identity $ fromMaybe "" $ IntMap.lookup $
getInt
>> >> "form_id" row >> >> >> >> <td>#{formId counties} >> >> <td>#{formId customers} >> >> -- maybe bind >> >> $bind someValue <- someMaybeValue >> >> >> >> <div>content >> >> >> >> -- maybe value was Nothing >> >> $nobind >> >> >> >> <div>other content >> >> >> >> -- not possible with identity bind possible place for >> >> >> >> error/warning >> >> >> >> $nobind >> >> >> >> <div>This should not happen! >> >> >> >> -- empty list >> >> $nobind >> >> >> >> <div>i left my content in my other pants >> >> >> >> >> yes, if you have a situation where many handlers are calling
the
>> >> >> same >> >> >> hamlet file, there might be some duplication, but then you >> >> >> can always raise >> >> >> the formId function to a top-level function. >> >> >> >> >> >> max >> >> >> >> >> >> On Apr 7, 2011, at 5:15 PM, Michael Snoyman wrote: >> >> >>> I've been very hesitant about adding more features to >> >> >>> Hamlet, especially ones that are already implemented in >> >> >>> Haskell.
That's
>> >> >>> been my >> >> >>> reasoning for avoiding any kind of variable definitions >> >> >>> until now. >> >> >>> However, >> >> >>> this does seem like a compelling use case. >> >> >>> >> >> >>> I don't think it would make sense to limit it to foralls: >> >> >>> it makes >> >> >>> as >> >> >>> much sense in maybes, and I think it would be confusing if >> >> >>> it only >> >> >>> applied >> >> >>> in some cases. As for syntax, how about: >> >> >>> >> >> >>> $forall row <- rs >> >> >>> >> >> >>> $let formId = fromMaybe "" $ IntMap.lookup $ getInt >> >> >>> >> >> >>> "form_id" >> >> >>> row >> >> >>> >> >> >>> ... >> >> >>> >> >> >>> I'm not 100% sold on this yet, what does everyone else >> >> >>> think? >> >> >>> >> >> >>> One last note: I'm probably going to be announcing a >> >> >>> feature freeze on >> >> >>> Yesod 0.8 *very* soon, and making a beta release to Yackage
so
>> >> >>> that people >> >> >>> can test. If you have any last-minute input, now's the >> >> >>> time. I'm >> >> >>> planning on >> >> >>> giving the beta test period about a week, and then >> >> >>> releasing
to
>> >> >>> Hackage. >> >> >>> >> >> >>> Michael >> >> >>> >> >> >>> On Thu, Apr 7, 2011 at 2:57 AM,
wrote:
>> >> >>> I noticed a pattern that in hamlet $forall i often retrieve
the
>> >> >>> same >> >> >>> value >> >> >>> from a map, Sometimes 3,4 times. >> >> >>> >> >> >>> $forall row <- rs >> >> >>> >> >> >>> <td>
row)}>#{getStr
>> >> >>> "form_name" >> >> >>> row} >> >> >>> >> >> >>> <td>#{getStr "docname" row} >> >> >>> ... >> >> >>> <td>#{fromMaybe "" (IntMap.lookup (getInt
"form_id"
>> >> >>> row) >> >> >>> counties)} >> >> >>> >> >> >>> <td>#{fromMaybe "" (IntMap.lookup (getInt
"form_id"
>> >> >>> row) >> >> >>> customers)} >> >> >>> >> >> >>> Would it be possible to allow let statement in forall for
often
>> >> >>> used >> >> >>> values ? >> >> >>> >> >> >>> Regards, >> >> >>> Vagif Verdi >> >> >>> >> >> >>> _______________________________________________ >> >> >>> web-devel mailing list >> >> >>> web-devel@haskell.org >> >> >>> http://www.haskell.org/mailman/listinfo/web-devel >> >> >>> >> >> >>> _______________________________________________ >> >> >>> web-devel mailing list >> >> >>> web-devel@haskell.org >> >> >>> http://www.haskell.org/mailman/listinfo/web-devel >> >> >> >> >> >> _______________________________________________ >> >> >> web-devel mailing list >> >> >> web-devel@haskell.org >> >> >> http://www.haskell.org/mailman/listinfo/web-devel >> >> > >> >> > -- >> >> > -barkmadley >> >> > sent from an internet enabled device >> >> >> >> -- >> >> -barkmadley >> >> sent from an internet enabled device >> >> -- >> -barkmadley >> sent from an internet enabled device
-- -barkmadley sent from an internet enabled device
-- -barkmadley sent from an internet enabled device
_______________________________________________ web-devel mailing list web-devel@haskell.org http://www.haskell.org/mailman/listinfo/web-devel
-- -barkmadley sent from an internet enabled device

I propose allowing : $with a <- b, c <- d : xyz [I already tried to send this once, but it bounced due to too much quoted text. So, sorry if some of you got this mail more than once.]

On Fri, Apr 8, 2011 at 8:20 PM, Aristid Breitkreuz
I propose allowing
: $with a <- b, c <- d : xyz
[I already tried to send this once, but it bounced due to too much quoted text. So, sorry if some of you got this mail more than once.]
Mark has already implemented this feature, and I've pulled it into the master branch. It will be a part of the 0.8 release. Thanks Mark! Michael

Mark Bradley wrote:
$with definitely differentiates it from the way that haskell does let binding and even makes it more obvious about the scoping (with bindings in languages like python/javascript work this way), even hinting that it doesn't to pattern matching.
You don't need to wander to Python and JS. "With" is a well-established idiom in Haskell. Just hoogle "with" and you'll see. This usage fits in with that perfectly. Michael Snoyman wrote:
for consistency, I'll use <- instead of =.
I'm not a user of this, so I am not expressing an opinion here. But just as an information point, <- is not consistent with the usual Haskell "with" idiom either. All of the other examples would use "$". I.e., "with" is a function, not new syntax. "$forall" reminds me of list comprehensions, which is why <- looks natural to me there. -Yitz

On Thursday, April 07, 2011 02:51:40 AM you wrote:
put me in the opposed category.
You can just as easily put: let formId rs = fromMaybe "" $ lookup $...
in the haskell function that loads the hamlet file t
You are missing the point. I cannot put anything inside haskell for a loop that is defined inside hamlet. Variable binding must happen inside forall loop, and variable is different for each iteration of the loop. It's just used in several places inside the loop block. There's no way to help it from the outside of the loop. That's why i am asking for binding only for $forall, because in all other cases we can indeed define all often used variables in haskell code.
hen you just have to put #{formId rs}
in the hamlet. I think adding syntax should be done only when very necessary. seems like a very small win here at a big cost.
yes, if you have a situation where many handlers are calling the same hamlet file, there might be some duplication, but then you can always raise the formId function to a top-level function.
max
On Apr 7, 2011, at 5:15 PM, Michael Snoyman wrote:
I've been very hesitant about adding more features to Hamlet, especially ones that are already implemented in Haskell. That's been my reasoning for avoiding any kind of variable definitions until now. However, this does seem like a compelling use case.
I don't think it would make sense to limit it to foralls: it makes as much sense in maybes, and I think it would be confusing if it only applied in some cases. As for syntax, how about:
$forall row <- rs
$let formId = fromMaybe "" $ IntMap.lookup $ getInt "form_id" row ...
I'm not 100% sold on this yet, what does everyone else think?
One last note: I'm probably going to be announcing a feature freeze on Yesod 0.8 *very* soon, and making a beta release to Yackage so that people can test. If you have any last-minute input, now's the time. I'm planning on giving the beta test period about a week, and then releasing to Hackage.
Michael
On Thu, Apr 7, 2011 at 2:57 AM,
wrote: I noticed a pattern that in hamlet $forall i often retrieve the same value from a map, Sometimes 3,4 times. $forall row <- rs
row}
<td>#{getStr "docname" row} ... <td>#{fromMaybe "" (IntMap.lookup (getInt "form_id" row)
counties)}
<td>#{fromMaybe "" (IntMap.lookup (getInt "form_id" row)
customers)}
Would it be possible to allow let statement in forall for often used values ?
Regards, Vagif Verdi
_______________________________________________ web-devel mailing list web-devel@haskell.org http://www.haskell.org/mailman/listinfo/web-devel
_______________________________________________ web-devel mailing list web-devel@haskell.org http://www.haskell.org/mailman/listinfo/web-devel

On Fri, Apr 8, 2011 at 2:37 AM,
On Thursday, April 07, 2011 02:51:40 AM you wrote:
put me in the opposed category.
You can just as easily put: let formId rs = fromMaybe "" $ lookup $...
in the haskell function that loads the hamlet file t
You are missing the point. I cannot put anything inside haskell for a loop that is defined inside hamlet. Variable binding must happen inside forall loop, and variable is different for each iteration of the loop. It's just used in several places inside the loop block. There's no way to help it from the outside of the loop.
the suggestion was for you to define a function that can be applied to the loop variable to make the code shorter.
That's why i am asking for binding only for $forall, because in all other cases we can indeed define all often used variables in haskell code.
hen you just have to put #{formId rs}
in the hamlet. I think adding syntax should be done only when very necessary. seems like a very small win here at a big cost.
yes, if you have a situation where many handlers are calling the same hamlet file, there might be some duplication, but then you can always raise the formId function to a top-level function.
max
On Apr 7, 2011, at 5:15 PM, Michael Snoyman wrote:
I've been very hesitant about adding more features to Hamlet, especially ones that are already implemented in Haskell. That's been my reasoning for avoiding any kind of variable definitions until now. However, this does seem like a compelling use case.
I don't think it would make sense to limit it to foralls: it makes as much sense in maybes, and I think it would be confusing if it only applied in some cases. As for syntax, how about:
$forall row <- rs
$let formId = fromMaybe "" $ IntMap.lookup $ getInt "form_id" row ...
I'm not 100% sold on this yet, what does everyone else think?
One last note: I'm probably going to be announcing a feature freeze on Yesod 0.8 *very* soon, and making a beta release to Yackage so that people can test. If you have any last-minute input, now's the time. I'm planning on giving the beta test period about a week, and then releasing to Hackage.
Michael
On Thu, Apr 7, 2011 at 2:57 AM,
wrote: I noticed a pattern that in hamlet $forall i often retrieve the same value from a map, Sometimes 3,4 times. $forall row <- rs
row}
<td>#{getStr "docname" row} ... <td>#{fromMaybe "" (IntMap.lookup (getInt "form_id" row)
counties)}
<td>#{fromMaybe "" (IntMap.lookup (getInt "form_id" row)
customers)}
Would it be possible to allow let statement in forall for often used values ?
Regards, Vagif Verdi
_______________________________________________ web-devel mailing list web-devel@haskell.org http://www.haskell.org/mailman/listinfo/web-devel
_______________________________________________ web-devel mailing list web-devel@haskell.org http://www.haskell.org/mailman/listinfo/web-devel
_______________________________________________ web-devel mailing list web-devel@haskell.org http://www.haskell.org/mailman/listinfo/web-devel
-- -barkmadley sent from an internet enabled device

Michael Snoyman wrote:
I'm probably going to be announcing a feature freeze on Yesod 0.8 *very* soon, and making a beta release to Yackage so that people can test. If you have any last-minute input, now's the time.
I personally would prefer if yackage --title would also change the title as it appears on the Yackage page itself in the <h1>, not just the <title>. But I'd be happy to hear other people's opinions. Thanks, Yitz

On Thu, Apr 7, 2011 at 1:20 PM, Yitzchak Gale
Michael Snoyman wrote:
I'm probably going to be announcing a feature freeze on Yesod 0.8 *very* soon, and making a beta release to Yackage so that people can test. If you have any last-minute input, now's the time.
I personally would prefer if yackage --title would also change the title as it appears on the Yackage page itself in the <h1>, not just the <title>. But I'd be happy to hear other people's opinions.
Thanks, Yitz
OK, patch is applied, and the change will be in the next release of Yackage, together with the proper localhost binding code. This has to wait until the 0.8 release of Yesod. Actually, if you want, you'll be able to install the beta version from the Yesod Yackage server soon (yo dawg...) Michael
participants (6)
-
Aristid Breitkreuz
-
Mark Bradley
-
Max Cantor
-
Michael Snoyman
-
vagif.verdi@gmail.com
-
Yitzchak Gale