Emacs模式编辑JSON

时间:2009-01-12 15:54:58

标签: json emacs unicode

有人知道一个好的Emacs模式来编辑JSON吗?我正在开发的一个应用程序使用基于JSON的通信协议,并且数据很好地缩进并且语法突出显示将在帮助我解决它的过程中帮助我很多。

12 个答案:

答案 0 :(得分:31)

Josh json-mode

+1 - 对我来说效果很好。我添加了

(defun beautify-json ()
  (interactive)
  (let ((b (if mark-active (min (point) (mark)) (point-min)))
        (e (if mark-active (max (point) (mark)) (point-max))))
    (shell-command-on-region b e
     "python -m json.tool" (current-buffer) t)))

(define-key json-mode-map (kbd "C-c C-f") 'beautify-json)

到json-mode.el使shell命令调用更容易。

更新:对于那些需要/希望使用unicode执行此操作的人,请参阅我的问题here。结果不是使用:

python -m json.tool

你想要使用

python -c 'import sys,json; data=json.loads(sys.stdin.read()); print json.dumps(data,sort_keys=True,indent=4).decode("unicode_escape").encode("utf8","replace")'

这既可以美化JSON,也可以保留原始的Unicode内容。

答案 1 :(得分:28)

js-mode支持json文件的语法高亮和缩进。

这与Emacs 23.2 相同,当espresso模式合并到Emacs并重命名为js-mode时。

检查出来: http://www.nongnu.org/espresso/

答案 2 :(得分:16)

你有没有试过Steve Yegge的js2-mode for Emacs

答案 3 :(得分:15)

如果你想要轻量级的东西,试试这个主要模式我一起入侵:https://github.com/joshwnj/json-mode

它实际上只是在javascript-mode之上突出显示的一些额外语法,但出于我的目的,我发现它工作得很好。

另一个常见的用例是自动格式化JSON文件(例如,如果它是空白压缩的,并且您希望更具可读性)。为此,我只是通过命令行脚本来管理缓冲区:C-u M- |

答案 4 :(得分:9)

我为js2-mode准备了一种解决方法,因此它可以无错误地解析json文件。 您可以在我的评论中找到它:http://code.google.com/p/js2-mode/issues/detail?id=50#c7

(我想把它作为评论发表J.F.Sebastian解决方案,但似乎我不允许这样做(没有'添加评论'链接))

答案 5 :(得分:4)

Edward O'Connor的

json.el是自23.1(2008)以来GNU Emacs的一部分。

虽然它不是语法高亮显示器,但它具有格式化JSON的有用功能:

M-x json-pretty-print-buffer RET

因此,如果您有最新版本的Emacs,则无需jqpython -m json.tool

答案 6 :(得分:3)

由于JSON是YAML的子集,yaml-mode也有效(我不知道它与js-modejson-mode的对比情况。)

安装(来自emacs):M-x package-install yaml-mode

yaml-mode~/.emacs.d/init.el与YAML和JSON文件的关联:

(add-to-list 'auto-mode-alist '("\\.yaml$" . yaml-mode))
(add-to-list 'auto-mode-alist '("\\.json$" . yaml-mode))

答案 7 :(得分:0)

espresso-mode

支持JSON

答案 8 :(得分:0)

JS3模式:https://github.com/thomblake/js3-mode

js3-mode是一个改进的js2-mode

此软件包可以通过package-list-packages命令安装

答案 9 :(得分:0)

我也将推出Josh的json模式,但也推荐使用flymake-json作为补充。它有助于突出语法错误。

我不喜欢使用python -mjson.tool,因为它会重新排序JSON对象中的项目。 我发现(prog-indent-sexp)可以很好地重新启动,并使用jsonlint 而不是python -mjson.tool适用于beautify-json

中的漂亮打印/重新格式化
(eval-after-load "json-mode"
  '(progn
     (require 'flymake-json)
     ;; flymake-cursor displays error in minibuffer message area instead of requiring hover
     (require 'flymake-cursor)

     (add-hook 'json-mode-hook 'flymake-json-load)
     (define-key json-mode-map "\C-c\C-n" (function flymake-goto-next-error))
  )
)

答案 10 :(得分:0)

我已经扩展了Mariusz Nowak的workaround,使其可以作为一种主要模式使用。除了简单地推导模式之外,还需要很少的修改; Nowak的工作实际需要的唯一变化是能够识别与文件无关的缓冲区,或与名称不以.json结尾的文件相关联的缓冲区,作为JSON,我们用缓冲区局部变量完成。

以下是增强的解决方法:

(make-variable-buffer-local 'js2-parse-as-json)

(defadvice js2-reparse (before json)
    (setq js2-buffer-file-name buffer-file-name))
(ad-activate 'js2-reparse)

(defadvice js2-parse-statement (around json)
    (if (and (= tt js2-LC)
           js2-buffer-file-name
           (or js2-parse-as-json
               (string-equal (substring js2-buffer-file-name -5) ".json"))
           (eq (+ (save-excursion
                    (goto-char (point-min))
                    (back-to-indentation)
                    (while (eolp)
                      (next-line)
                      (back-to-indentation))
                    (point)) 1) js2-ts-cursor))
      (setq ad-return-value (js2-parse-assign-expr))
        ad-do-it))
(ad-activate 'js2-parse-statement)

(define-derived-mode json-mode js2-mode "JSON"
  "Major mode for editing JSON data."
  :group 'json
  (setq js2-parse-as-json t)
  (js2-reparse t))

(add-to-list 'auto-mode-alist '("\\.json$" . json-mode))

如果你已经使用js2-mode,这可能是比js-modeflymake-json更好的选择,因为你不需要安装任何新东西(js2-mode已经进行语法检查,不需要外部工具),因为这种模式将继承你的js-mode配置,js-mode不会。

答案 11 :(得分:-6)

我还建议使用js2-mode。

JSON代表JavaScript Object Notation。它不是另一种语言,它甚至不是像yaml或xml这样的数据容器。如果在JSON对象中没有函数(或者在本例中我们应该说方法),JSON可以用作数据容器,但它不是JSON的主要目标: - )

var myJSObject = {
  attr: {foo: "bar", baz: ["quux", "truc", "pouet"]},
  fooAlert: function (num) {
    alert(this.attr.foo+' '+num);
  }
};
myJSObject.fooAlert(42);