1

Using Vue.JS 1.0, I couldn't find a simple way to properly format a JSON date that can be empty.

I tried with vue-filter npm package date filter but it fails if the date is empty. For example if my data is:

{ name: "John", birthday: null },  /* unknown birthday */
{ name: "Maria", birthday: "2012-04-23T18:25:43.511Z" },

returns

John 12/31/1969 9:00:00 PM  <-- null date should be blank 
Maria 4/23/2012 3:25:43 PM  <-- ok

The code i am using:

<!DOCTYPE html><html>
<head>
    <script src="lib/vue/dist/vue.min.js"></script>
    <script src="lib/vue-filter/dist/vue-filter.min.js"></script>
</head>
<body>
<div id="app">
    <h1>Without Filter:</h1>
    <div v-for="person in list">
        <div>{{person.name}}  {{person.birthday}}</div>
    </div>
    <h1>With Filter:</h1>
    <div v-for="person in list">
        <div>{{person.name}}  {{person.birthday | date }}</div>
    </div>
</div>
<script>
    new Vue({
        el: "#app",
        data: {
            list: [
                { name: "John", birthday: null },
                { name: "Maria", birthday: "2012-04-23T18:25:43.511Z" },
            ]
        }
    });
</script>
</body>
</html>

What is the proper way to format a date, that will also make show blank if date is null?

2 Answers 2

2

Write a custom filter to wrap the date filter. If the input is null, return null, otherwise return Vue.filter('date')(input)

Vue.filter('dateOrNull', function(d, ...others) {
  return d ? Vue.filter('date')(d, ...others) : null;
});
new Vue({
  el: "#app",
  data: {
    list: [{
      name: "John",
      birthday: null
    }, {
      name: "Maria",
      birthday: "2012-04-23T18:25:43.511Z"
    }, ]
  }
});
<script src="//cdnjs.cloudflare.com/ajax/libs/vue/1.0.26/vue.min.js"></script>
<script src="//rawgit.com/wy-ei/vue-filter/master/dist/vue-filter.min.js"></script>
<div id="app">
  <h1>Without Filter:</h1>
  <div v-for="person in list">
    <div>{{person.name}} {{person.birthday}}</div>
  </div>
  <h1>With Filter:</h1>
  <div v-for="person in list">
    <div>{{person.name}} {{person.birthday | dateOrNull '%B'}}</div>
  </div>
</div>

Sign up to request clarification or add additional context in comments.

3 Comments

Do you know how to pass through parameters from dateOrNull to date? As in {{person.birthday | dateOrNull '%B' }}
Modern JS has the spread operator. See updated example. Older JS would do Vue.filter('date').apply(null, arguments)
I prefer the later in order to support more browsers. Thanks!
1

It doesn't work well:

Roy answers exactly what I asked. But it turned out that vue-filter was not good for my needs. I needed '%c' to show date in browser's locale format (bad idea). vue-filter source was actually doing the following: (rewrited as a stand alone filter, to avoid the dependency):

Vue.filter('date', function (d) {
    var date = new Date(d);
    return d ? date.toLocaleDateString() + ' ' + date.toLocaleTimeString().trim() : null;
});

It is terrible: each browser works differently. And dates with unknown timezone are assumed UTC and moved to local timezone causing this when living at GMT-3: javascript toLocaleDateString screws timezones

New plan:

Use Moment.js with a custom filter:

Vue.filter('moment', function (date) {
    var d = moment(date);
    if (!d.isValid(date)) return null;
    return d.format.apply(d, [].slice.call(arguments, 1));
});

Don't forget <script src='moment.js'>.

Usage: {{ date | moment "dddd, MMMM Do YYYY" }}

See also: Moment Date and Time Format Strings

I also tried vue-moment npm package BUT it depends on CommonJS / require() syntax, and I don't want to use webpack/browserify just for this,

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.