WhoopInc / frozen-moment-OLD

NOW A MOMENT PLUGIN:
https://github.com/WhoopInc/frozen-moment
MIT License
9 stars 0 forks source link

Syntax sugar for single "mutations" #4

Open butterflyhug opened 10 years ago

butterflyhug commented 10 years ago

instance.thaw().mutate().freeze() is kind of wordy if you just want to generate a new FrozenMoment while applying a single mutation method on the builder.

If we offer a convenience syntax for this, I'm currently biased toward something like instance.copy.mutate() instead of replicating moment's current API, because I think it'll be confusing if we implement a moment API method name with different semantics. (Especially for setters.) Note that multiple mutations with this syntax would be instance.copy.mutate().copy.mutate() -- I feel like that would start to push people back toward the more efficient builder syntax for those use cases, which also seems like a feature of this approach.

butterflyhug commented 10 years ago

On second thought, nested object namespaces don't work because this.

I'm currently leaning toward prefixing all the convenience mutators and setters with to, indicating that it's a conversion of the object (and thus a copy) as with toISOString or toDate. So, we'd have things like moment().toStartOf("day"), moment().toMonth(5), and moment().toLocale("fr").

So far, so good. Unfortunately, this doesn't work as well with add and subtract. For example, moment().toAdd(3, "days") doesn't read well at all. But, I'm not immediately thinking of better alternatives that don't totally break the consistency of the API design... part of the problem is that these APIs aren't named consistently in upstream Moment, because add and subtract are active verbs and most of the other methods are trying to be noun phrases.

(get and set are also verbs, but get is irrelevant here and I think I'm okay with skipping the convenience wrapper for set.)

butterflyhug commented 10 years ago

Here's a completely wacky idea:

moment().add(5, "days")       =>  frozenMoment().to(5, "days").later
moment().subtract(5, "days")  =>  frozenMoment().to(5, "days").earlier

Alternatively, "later" / "earlier" could be a required third parameter:

frozenMoment().to(5, "days", "later")
frozenMoment().to(5, "days", "earlier")
butterflyhug commented 10 years ago

Note that moment#1793 proposes to use moment().to(moment()) as a way to create durations.