4

The json package coming with Emacs 24 has function json-encode that works like this:

(json-encode '(("key" . "value")))
"{\"key\":\"value\"}"

In case there are no keys (object is empty) I get:

(json-encode '())
"null"

when in this case I need to get an empty object:

(json-encode '())
"{}"
  1. Is there a way to make json encode empty alist or plist as {}?
  2. Is there another json package that can do this?
Stefan
  • 26,154
  • 3
  • 46
  • 84
Gracjan Polak
  • 1,082
  • 6
  • 21
  • `(json-encode #s(hash-table))`, but I don't think there's a way to do that with lists. – wvxvw Nov 07 '15 at 09:56
  • Does `json-encode-alist` or `json-encode-plist` work for you? On Emacs 25, both `(json-encode-alist '())` and `(json-encode-plist '())` give "{}". – xuchunyang Nov 07 '15 at 10:02
  • @xuchunyang: I do not think it work recursively, nested objects have same issue. – Gracjan Polak Nov 07 '15 at 11:41
  • @wvxvw: Thanks for the tip, I'll look at this. – Gracjan Polak Nov 07 '15 at 11:41
  • Looks like a bug to me. `M-x report-emacs-bug`. Is there a clearly defined spec (e.g., in the doc string or at least the code comments) of the parameter to `json-encode`? If so, what does it say about a value of `()`? If not, consider at least filing a doc bug - all parameters to functions should be clearly specified in the doc string. – Drew Nov 07 '15 at 15:26

1 Answers1

4

It's unlikely that there will be a solution here that will satisfy every user of the json package, since the problem is that elisp and json have differing semantics. In Lisp, the empty list and the lack of a value (nil) are the same thing. In Javascript (and therefore JSON), the empty array, the "empty" object, the boolean false value, and a lack of a value are three different things. Any mapping between Lisp and Javascript will thus be a matter of compromises.

I recommend defining some advice which changes how json-encode works; just test to see if the object argument is nil and return what you want:

(defadvice json-encode (around encode-nil-as-json-empty-object activate)
  (if (null object)
    (setq ad-return-value "{}")
    ad-do-it))

This will work in the normal recursive case, as the advice will modify the definition of json-encode; the recursive calls will naturally call the modified code.

db48x
  • 15,741
  • 1
  • 19
  • 23
  • 1
    In the [project page](https://github.com/thorstadt/json.el) I read "since false and null are distinct in JSON, you can distinguish them by binding json-false and json-null as desired.", won't that help ? – Ehvince Jun 14 '17 at 10:55