diff --git a/.circleci/config.yml b/.circleci/config.yml index def610ed..14043b78 100644 --- a/.circleci/config.yml +++ b/.circleci/config.yml @@ -1,56 +1,131 @@ version: 2.1 -# Default actions to perform on each Emacs version -default: &default-steps - steps: - - checkout - - run: apt-get update && apt-get install make - - run: make elpa - - run: emacs --version - - run: make test - # Make sure to run test-checks before test-bytecomp, as test-bytecomp autogenerates - # files which won't pass test-checks. - - run: make test-checks - - run: make test-bytecomp +orbs: + win: circleci/windows@2.2.0 + +commands: + setup: + steps: + - checkout + - run: + name: Install Eldev + command: curl -fsSL https://raw.github.com/doublep/eldev/master/webinstall/circle-eldev > x.sh && source ./x.sh + + setup-macos: + steps: + - checkout + - run: + name: Install Emacs latest + command: | + brew install homebrew/cask/emacs + - run: + name: Install Eldev + command: curl -fsSL https://raw.github.com/doublep/eldev/master/webinstall/circle-eldev > x.sh && source ./x.sh + + setup-windows: + steps: + - checkout + - run: + name: Install Eldev + command: | + # Remove expired DST Root CA X3 certificate. Workaround + # for https://debbugs.gnu.org/cgi/bugreport.cgi?bug=51038 + # bug on Emacs 27.2. + gci cert:\LocalMachine\Root\DAC9024F54D8F6DF94935FB1732638CA6AD77C13 + gci cert:\LocalMachine\Root\DAC9024F54D8F6DF94935FB1732638CA6AD77C13 | Remove-Item + (iwr https://raw.github.com/doublep/eldev/master/webinstall/circle-eldev.ps1).Content | powershell -command - + test: + steps: + - run: + name: Run regression tests + command: eldev -dtT -p test + lint: + steps: + - run: + name: Lint + command: eldev lint -c + compile: + steps: + - run: + name: Check for byte-compilation errors + command: eldev -dtT compile --warnings-as-errors -# Enumerated list of Emacs versions jobs: - test-emacs-25: + test-ubuntu-emacs-26: docker: - - image: silex/emacs:25-ci-cask + - image: silex/emacs:26-ci entrypoint: bash - <<: *default-steps - - test-emacs-26: + steps: + - setup + - test + - lint + - compile + test-ubuntu-emacs-27: docker: - - image: silex/emacs:26-ci-cask + - image: silex/emacs:27-ci entrypoint: bash - <<: *default-steps - - test-emacs-27: + steps: + - setup + - test + - lint + - compile + test-ubuntu-emacs-28: docker: - - image: silex/emacs:27-ci-cask + - image: silex/emacs:28-ci entrypoint: bash - <<: *default-steps - - test-emacs-28: + steps: + - setup + - test + - lint + - compile + test-ubuntu-emacs-29: docker: - - image: silex/emacs:28-ci-cask + - image: silex/emacs:29-ci entrypoint: bash - <<: *default-steps - - test-emacs-master: + steps: + - setup + - test + - lint + - compile + test-ubuntu-emacs-master: docker: - - image: silex/emacs:master-ci-cask + - image: silex/emacs:master-ci entrypoint: bash - <<: *default-steps + steps: + - setup + - test + - lint + - compile + test-macos-emacs-latest: + macos: + xcode: "14.2.0" + steps: + - setup-macos + - test + - lint + - compile + test-windows-emacs-latest: + executor: win/default + steps: + - run: + name: Install Emacs latest + command: | + choco install emacs -y + - setup-windows + - test + - lint + - compile workflows: - version: 2 + version: 2.1 ci-test-matrix: jobs: - - test-emacs-25 - - test-emacs-26 - - test-emacs-27 - - test-emacs-28 - - test-emacs-master + - test-ubuntu-emacs-26 + - test-ubuntu-emacs-27 + - test-ubuntu-emacs-28 + - test-ubuntu-emacs-29 + - test-ubuntu-emacs-master + - test-windows-emacs-latest + - test-macos-emacs-latest: + requires: + - test-ubuntu-emacs-29 diff --git a/.github/FUNDING.yml b/.github/FUNDING.yml index 24e86434..718dd0d1 100644 --- a/.github/FUNDING.yml +++ b/.github/FUNDING.yml @@ -2,7 +2,5 @@ github: bbatsov patreon: bbatsov -ko_fi: bbatsov open_collective: cider -liberapay: bbatsov custom: https://www.paypal.me/bbatsov diff --git a/.github/ISSUE_TEMPLATE.md b/.github/ISSUE_TEMPLATE/bug_report.md similarity index 88% rename from .github/ISSUE_TEMPLATE.md rename to .github/ISSUE_TEMPLATE/bug_report.md index 421e8683..dcf8bb8e 100644 --- a/.github/ISSUE_TEMPLATE.md +++ b/.github/ISSUE_TEMPLATE/bug_report.md @@ -1,3 +1,9 @@ +--- +name: Bug Report +about: Report an issue with clojure-mode you've discovered. +labels: [bug] +--- + *Use the template below when reporting bugs. Please, make sure that you're running the latest stable clojure-mode and that the problem you're reporting hasn't been reported (and potentially fixed) already.* diff --git a/.gitignore b/.gitignore index ef07d5a4..360a9941 100644 --- a/.gitignore +++ b/.gitignore @@ -9,3 +9,6 @@ elpa* /clojure-mode-autoloads.el /clojure-mode-pkg.el + +/.eldev +/Eldev-local diff --git a/CHANGELOG.md b/CHANGELOG.md index 95d426e6..51077f9e 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -2,6 +2,48 @@ ## master (unreleased) +## 5.20.0 (2025-05-27) + +### New features + +* Add `clojuredart-mode`, `joker-mode` and `jank-mode`, derived from `clojure-mode`. + +### Bugs fixed + +* [cider#3758](https://github.com/clojure-emacs/cider/issues/3758): Improve regexp for `clojure-find-def` to recognize more complex metadata on vars. +* [#684](https://github.com/clojure-emacs/clojure-mode/issues/684): Restore `outline-regexp` pattern to permit outline handling of top-level forms. +* Improve regexp for `clojure-find-def` to recognize `defn-` and other declarations on the form `def...-`. + +## 5.19.0 (2024-05-26) + +### Bugs fixed + +* Fix `clojure-align` when called from `clojure-ts-mode` major mode buffers. +* [#671](https://github.com/clojure-emacs/clojure-mode/issues/671): Syntax highlighting for digits after the first in `%` args. (e.g. `%10`) +* [#680](https://github.com/clojure-emacs/clojure-mode/issues/680): Change syntax class of ASCII control characters to punctuation, fixing situations where carriage returns were being interpreted as symbols. + +# Changes + +* [#675](https://github.com/clojure-emacs/clojure-mode/issues/675): Add `.lpy` to the list of known Clojure file extensions. + +## 5.18.1 (2023-11-24) + +### Bugs fixed + +* [#653](https://github.com/clojure-emacs/clojure-mode/issues/653): Don't highlight vars with colons as keywords. + +## 5.18.0 (2023-10-18) + +### Changes + +* [cider#2903](https://github.com/clojure-emacs/cider/issues/2903): Avoid `No comment syntax is defined` prompts. + +## 5.17.1 (2023-09-12) + +### Changes + +* Declare indentation for the `async` ClojureScript macro. + ## 5.17.0 (2023-09-11) ### Changes @@ -10,15 +52,14 @@ ### Bugs fixed -* [#656](https://github.com/clojure-emacs/clojure-mode/issues/656): Fix clojure-find-ns when ns form is preceded by other forms. - -* [#593](https://github.com/clojure-emacs/clojure-mode/issues/593): Fix clojure-find-ns when ns form is preceded by whitespace or inside comment form. +* [#656](https://github.com/clojure-emacs/clojure-mode/issues/656): Fix `clojure-find-ns` when ns form is preceded by other forms. +* [#593](https://github.com/clojure-emacs/clojure-mode/issues/593): Fix `clojure-find-ns` when ns form is preceded by whitespace or inside comment form. ## 5.16.2 (2023-08-23) ### Changes -* `clojure-find-ns`: add an option to never raise errors, returning nil instead on unparseable ns forms. +* `clojure-find-ns`: add an option to never raise errors, returning `nil` instead on unparseable ns forms. ## 5.16.1 (2023-06-26) @@ -42,7 +83,7 @@ * [#581](https://github.com/clojure-emacs/clojure-mode/issues/581): Fix font locking not working for keywords starting with a number. * [#377](https://github.com/clojure-emacs/clojure-mode/issues/377): Fix everything starting with the prefix `def` being highlighted as a definition form. Now definition forms are enumerated explicitly in the font-locking code, like all other forms. -* [#638](https://github.com/clojure-emacs/clojure-mode/pull/638): Fix imenu with Clojure code in string or comment. +* [#638](https://github.com/clojure-emacs/clojure-mode/pull/638): Fix `imenu` with Clojure code in string or comment. ## 5.15.1 (2022-07-30) diff --git a/CONTRIBUTING.md b/CONTRIBUTING.md index 2743702a..2eada5b9 100644 --- a/CONTRIBUTING.md +++ b/CONTRIBUTING.md @@ -39,8 +39,8 @@ and description in grammatically correct, complete sentences. ## Development setup 1. Fork and clone the repository. -1. Install [Cask][7]. -1. Run `cask install` in the repository folder. +1. Install [Eldev][7]. +1. Run `eldev build` in the repository folder. 1. Run tests with `make test`. **Note:** macOS users should make sure that the `emacs` command resolves the version of Emacs they've installed @@ -53,5 +53,5 @@ See [this article][8] for more details. [4]: https://help.github.com/articles/using-pull-requests [5]: https://gitready.com/advanced/2009/02/10/squashing-commits-with-rebase.html [6]: https://github.com/clojure-emacs/clojure-mode/blob/master/CHANGELOG.md -[7]: https://github.com/cask/cask +[7]: https://github.com/emacs-eldev/eldev [8]: https://emacsredux.com/blog/2015/05/09/emacs-on-os-x/ diff --git a/Cask b/Cask deleted file mode 100644 index abcd75fd..00000000 --- a/Cask +++ /dev/null @@ -1,9 +0,0 @@ -(source gnu) -(source melpa) - -(package-file "clojure-mode.el") - -(development - (depends-on "s") - (depends-on "buttercup") - (depends-on "paredit")) diff --git a/Eldev b/Eldev new file mode 100644 index 00000000..1becee18 --- /dev/null +++ b/Eldev @@ -0,0 +1,26 @@ +; -*- mode: emacs-lisp; lexical-binding: t -*- + +(eldev-require-version "1.6") + +(eldev-use-package-archive 'gnu-elpa) +(eldev-use-package-archive 'nongnu-elpa) +(eldev-use-package-archive 'melpa) + +(eldev-use-plugin 'autoloads) + +(eldev-add-extra-dependencies 'test 'paredit 's 'buttercup) + +(setq byte-compile-docstring-max-column 240) +(setq checkdoc-force-docstrings-flag nil) +(setq checkdoc-permit-comma-termination-flag t) +(setq checkdoc--interactive-docstring-flag nil) + +(setf eldev-lint-default '(elisp)) + +(with-eval-after-load 'elisp-lint + ;; We will byte-compile with Eldev. + (setf elisp-lint-ignored-validators '("package-lint" "fill-column" "byte-compile" "checkdoc") + enable-local-variables :safe + elisp-lint-indent-specs '((define-clojure-indent . 0)))) + +(setq eldev-project-main-file "clojure-mode.el") diff --git a/Makefile b/Makefile index 27503963..3e613538 100644 --- a/Makefile +++ b/Makefile @@ -1,42 +1,17 @@ -CASK = cask -export EMACS ?= emacs -EMACSFLAGS = - -PKGDIR := $(shell EMACS=$(EMACS) $(CASK) package-directory) - -SRCS = $(wildcard *.el) -OBJS = $(SRCS:.el=.elc) - -.PHONY: compile test clean elpa - -all: compile - -elpa-$(EMACS): - $(CASK) install - $(CASK) update - touch $@ - -elpa: elpa-$(EMACS) - -elpaclean: - rm -f elpa* - rm -rf .cask # Clean packages installed for development - -compile: elpa - $(CASK) build +.PHONY: clean compile lint test all +.DEFAULT_GOAL := all clean: - rm -f $(OBJS) clojure-mode-autoloads.el + eldev clean -test: $(PKGDIR) - $(CASK) exec buttercup +lint: clean + eldev lint -c -test-checks: - $(CASK) exec $(EMACS) --no-site-file --no-site-lisp --batch \ - -l test/test-checks.el ./ +# Checks for byte-compilation warnings. +compile: clean + eldev -dtT compile --warnings-as-errors -test-bytecomp: $(SRCS:.el=.elc-test) +test: clean + eldev -dtT -p test -%.elc-test: %.el elpa - $(CASK) exec $(EMACS) --no-site-file --no-site-lisp --batch \ - -l test/clojure-mode-bytecomp-warnings.el $< +all: clean compile lint test diff --git a/README.md b/README.md index 7042486a..4845bbd3 100644 --- a/README.md +++ b/README.md @@ -11,13 +11,13 @@ highlighting), indentation, navigation and refactoring support for the [Clojure(Script) programming language](https://clojure.org). ------------ - -**This documentation tracks the `master` branch of `clojure-mode`. Some of -the features and settings discussed here might not be available in -older releases (including the current stable release). Please, consult -the relevant git tag (e.g. [5.17.0](https://github.com/clojure-emacs/clojure-mode/tree/v5.17.0)) if you need documentation for a -specific `clojure-mode` release.** +> [!IMPORTANT] +> +> This documentation tracks the `master` branch of `clojure-mode`. Some of the +> features and settings discussed here might not be available in older releases +> (including the current stable release). Please, consult the relevant git tag +> (e.g. [5.20.0](https://github.com/clojure-emacs/clojure-mode/tree/v5.20.0)) if +> you need documentation for a specific `clojure-mode` release. ## Installation @@ -47,9 +47,12 @@ If the installation doesn't work try refreshing the package list: The `clojure-mode` package actually bundles together several major modes: -* `clojure-mode` is a major mode for editing Clojure code -* `clojurescript-mode` is a major mode for editing ClojureScript code -* `clojurec-mode` is a major mode for editing `.cljc` source files +- `clojure-mode` is a major mode for editing Clojure code +- `clojurescript-mode` is a major mode for editing ClojureScript code +- `clojurec-mode` is a major mode for editing `.cljc` source files +- `clojuredart-mode` is a major mode for editing ClojureDart `.cljd` source files +- `jank-mode` is a major mode for editing Jank `.jank` source files +- `joker-mode` is a major mode for editing Joker `.joke` source files All the major modes derive from `clojure-mode` and provide more or less the same functionality. Differences can be found mostly in the font-locking - @@ -78,6 +81,17 @@ The default indentation rules in `clojure-mode` are derived from the [community Clojure Style Guide](https://guide.clojure.style). Please, refer to the guide for the general Clojure indentation rules. +If you'd like to use the alternative "fixed/tonsky" indentation style you should +update your configuration accordingly: + +``` el +(setq clojure-indent-style 'always-indent + clojure-indent-keyword-style 'always-indent + clojure-enable-indent-specs nil) +``` + +Read on for more details on the available indentation-related configuration options. + #### Indentation of docstrings By default multi-line docstrings are indented with 2 spaces, as this is a @@ -126,8 +140,47 @@ The indentation of function forms is configured by the variable 2) ``` -**Note:** Prior to clojure-mode 5.10, the configuration options for `clojure-indent-style` used to be -keywords, but now they are symbols. Keywords will still be supported at least until clojure-mode 6. +> [!NOTE] +> +> Prior to clojure-mode 5.10, the configuration options for `clojure-indent-style` used to be +> keywords, but now they are symbols. Keywords will still be supported at least until clojure-mode 6. + +#### Indentation of keywords + +Similarly we have the `clojure-indent-keyword-style`, which works in the following way: + +- `always-align` (default) - All + args are vertically aligned with the first arg in case (A), + and vertically aligned with the function name in case (B). + +``` clojure +(:require [foo.bar] + [bar.baz]) +(:require + [foo.bar] + [bar.baz]) +``` + +- `always-indent` - All args are indented like a macro body. + +``` clojure +(:require [foo.bar] + [bar.baz]) +(:x + location + 0) +``` + +- `align-arguments` - Case (A) is indented like `always-align`, and + case (B) is indented like a macro body. + +``` clojure +(:require [foo.bar] + [bar.baz]) +(:x + location + 0) +``` #### Indentation of macro forms @@ -218,7 +271,13 @@ Setting `clojure-special-arg-indent-factor` to 1, results in: [my-field]) ``` -### Indentation of Comments +You can completely disable the effect of indentation specs like this: + +``` el +(setq clojure-enable-indent-specs nil) +``` + +#### Indentation of Comments `clojure-mode` differentiates between comments like `;`, `;;`, etc. By default `clojure-mode` treats `;` as inline comments and *always* indents those. @@ -231,7 +290,11 @@ You can change this behaviour like this: You might also want to change `comment-add` to 0 in that way, so that Emacs comment functions (e.g. `comment-region`) would use `;` by default instead of `;;`. -**Note:** Check out [this section](https://guide.clojure.style/#comments) of the Clojure style guide to understand better the semantics of the different comment levels and why `clojure-mode` treats them differently by default. +> [!TIP] +> +> Check out [this section](https://guide.clojure.style/#comments) of the Clojure +> style guide to understand better the semantics of the different comment levels +> and why `clojure-mode` treats them differently by default. ### Vertical alignment @@ -258,9 +321,11 @@ happen whenever you select some code and hit `TAB`. ### Font-locking -`clojure-mode` features static font-locking (syntax highlighting) that you can extend yourself -if needed. As typical for Emacs, it's based on regular expressions. You can find -the default font-locking rules in `clojure-font-lock-keywords`. Here's how you can add font-locking for built-in Clojure functions and vars: +`clojure-mode` features static font-locking (syntax highlighting) that you can +extend yourself if needed. As typical for Emacs, it's based on regular +expressions. You can find the default font-locking rules in +`clojure-font-lock-keywords`. Here's how you can add font-locking for built-in +Clojure functions and vars: ``` el (defvar clojure-built-in-vars @@ -303,9 +368,12 @@ var a symbol resolves to). That's why `clojure-mode`'s font-locking defaults are conservative and minimalistic. Precise font-locking requires additional data that can obtained from a running -REPL (that's how CIDER's [dynamic font-locking](https://docs.cider.mx/cider/config/syntax_highlighting.html) works) or from static code analysis. +REPL (that's how CIDER's [dynamic +font-locking](https://docs.cider.mx/cider/config/syntax_highlighting.html) +works) or from static code analysis. -When it comes to non built-in definitions, `clojure-mode` needs to be manually instructed how to handle the docstrings and highlighting. Here's an example: +When it comes to non built-in definitions, `clojure-mode` needs to be manually +instructed how to handle the docstrings and highlighting. Here's an example: ``` emacs-lisp (put '>defn 'clojure-doc-string-elt 2) @@ -316,7 +384,9 @@ When it comes to non built-in definitions, `clojure-mode` needs to be manually i 1 font-lock-keyword-face))) ``` -**Note:** The `clojure-doc-string-elt` attribute is processed by the function `clojure-font-lock-syntactic-face-function`. +> [!NOTE] +> +> The `clojure-doc-string-elt` attribute is processed by the function `clojure-font-lock-syntactic-face-function`. ## Refactoring support @@ -424,7 +494,7 @@ without affecting the namespace declaration. ## Related packages -* [clojure-mode-extra-font-locking][] provides additional font-locking +- [clojure-mode-extra-font-locking][] provides additional font-locking for built-in methods and macros. The font-locking is pretty imprecise, because it doesn't take namespaces into account and it won't font-lock a function at all possible positions in a sexp, but @@ -445,9 +515,9 @@ plenty of incorrect font-locking. CIDER users should avoid this package, as CIDER does its own dynamic font-locking, which is namespace-aware and doesn't produce almost any false positives. -* [clj-refactor][] provides refactoring support. +- [clj-refactor][] provides additional refactoring support. -* Enabling `CamelCase` support for editing commands(like +- Enabling `CamelCase` support for editing commands (like `forward-word`, `backward-word`, etc) in `clojure-mode` is quite useful since we often have to deal with Java class and method names. The built-in Emacs minor mode `subword-mode` provides such @@ -457,7 +527,7 @@ functionality: (add-hook 'clojure-mode-hook #'subword-mode) ``` -* The use of [paredit][] when editing Clojure (or any other Lisp) code +- The use of [paredit][] when editing Clojure (or any other Lisp) code is highly recommended. It helps ensure the structure of your forms is not compromised and offers a number of operations that work on code structure at a higher level than just characters and words. To enable @@ -467,7 +537,7 @@ it for Clojure buffers: (add-hook 'clojure-mode-hook #'paredit-mode) ``` -* [smartparens][] is an excellent +- [smartparens][] is an excellent (newer) alternative to paredit. Many Clojure hackers have adopted it recently and you might want to give it a try as well. To enable `smartparens` use the following code: @@ -476,7 +546,7 @@ it for Clojure buffers: (add-hook 'clojure-mode-hook #'smartparens-strict-mode) ``` -* [RainbowDelimiters][] is a +- [RainbowDelimiters][] is a minor mode which highlights parentheses, brackets, and braces according to their depth. Each successive level is highlighted in a different color. This makes it easy to spot matching delimiters, @@ -488,7 +558,7 @@ it for Clojure buffers: (add-hook 'clojure-mode-hook #'rainbow-delimiters-mode) ``` -* [aggressive-indent-mode][] automatically adjust the indentation of your code, +- [aggressive-indent-mode][] automatically adjust the indentation of your code, while you're writing it. Using it together with `clojure-mode` is highly recommended. Provided you've already installed `aggressive-indent-mode` you can enable it like this: @@ -497,6 +567,9 @@ enable it like this: (add-hook 'clojure-mode-hook #'aggressive-indent-mode) ``` +Note that it might cause performance issues if you're dealing with large +Clojure source files. + ## REPL Interaction One of the fundamental aspects of Lisps in general, and Clojure in @@ -540,22 +613,30 @@ experience negatively. ### General Issues -`clojure-mode` derives a lot of functionality directly from `lisp-mode` (an Emacs major mode for Common Lisp), which -simplified the initial implementation, but also made it harder to implement -certain functionality. Down the road it'd be nice to fully decouple `clojure-mode` -from `lisp-mode`. +`clojure-mode` derives a lot of functionality directly from `lisp-mode` (an +Emacs major mode for Common Lisp), which simplified the initial implementation, +but also made it harder to implement certain functionality. Down the road it'd +be nice to fully decouple `clojure-mode` from `lisp-mode`. See [this ticket](https://github.com/clojure-emacs/clojure-mode/issues/270) for a bit more details. ### Indentation Performance -`clojure-mode`'s indentation engine is a bit slow. You can speed things up significantly by disabling `clojure-use-backtracking-indent`, but this will break the indentation of complex forms like `deftype`, `defprotocol`, `reify`, `letfn`, etc. +`clojure-mode`'s indentation engine is a bit slow. You can speed things up +significantly by disabling `clojure-use-backtracking-indent`, but this will +break the indentation of complex forms like `deftype`, `defprotocol`, `reify`, +`letfn`, etc. -We should look into ways to optimize the performance of the backtracking indentation logic. See [this ticket](https://github.com/clojure-emacs/clojure-mode/issues/606) for more details. +We should look into ways to optimize the performance of the backtracking +indentation logic. See [this ticket](https://github.com/clojure-emacs/clojure-mode/issues/606) for more +details. ### Font-locking Implementation -As mentioned [above](https://github.com/clojure-emacs/clojure-mode#font-locking), the font-locking is implemented in terms of regular expressions which makes it both slow and inaccurate. +As mentioned +[above](https://github.com/clojure-emacs/clojure-mode#font-locking), the +font-locking is implemented in terms of regular expressions which makes it both +slow and inaccurate. ## Changelog @@ -563,7 +644,7 @@ An extensive changelog is available [here](CHANGELOG.md). ## License -Copyright © 2007-2023 Jeffrey Chu, Lennart Staflin, Phil Hagelberg, Bozhidar +Copyright © 2007-2025 Jeffrey Chu, Lennart Staflin, Phil Hagelberg, Bozhidar Batsov, Artur Malabarba, Magnar Sveen and [contributors][]. Distributed under the GNU General Public License; type C-h C-c to view it. diff --git a/clojure-mode.el b/clojure-mode.el index 8e0780a1..c3d950ce 100644 --- a/clojure-mode.el +++ b/clojure-mode.el @@ -1,7 +1,7 @@ ;;; clojure-mode.el --- Major mode for Clojure code -*- lexical-binding: t; -*- ;; Copyright © 2007-2013 Jeffrey Chu, Lennart Staflin, Phil Hagelberg -;; Copyright © 2013-2023 Bozhidar Batsov, Artur Malabarba, Magnar Sveen +;; Copyright © 2013-2025 Bozhidar Batsov, Artur Malabarba, Magnar Sveen ;; ;; Authors: Jeffrey Chu ;; Lennart Staflin @@ -12,7 +12,7 @@ ;; Maintainer: Bozhidar Batsov ;; URL: https://github.com/clojure-emacs/clojure-mode ;; Keywords: languages clojure clojurescript lisp -;; Version: 5.17.0 +;; Version: 5.20.0 ;; Package-Requires: ((emacs "25.1")) ;; This file is not part of GNU Emacs. @@ -100,6 +100,8 @@ (defcustom clojure-indent-style 'always-align "Indentation style to use for function forms and macro forms. +For forms that start with a keyword see `clojure-indent-keyword-style'. + There are two cases of interest configured by this variable. - Case (A) is when at least one function argument is on the same @@ -147,6 +149,50 @@ to indent function forms. align-arguments)) :package-version '(clojure-mode . "5.2.0")) +(defcustom clojure-indent-keyword-style 'always-align + "Indentation style to use for forms that start with a keyword. +For function/macro forms, see `clojure-indent-style'. +There are two cases of interest configured by this variable. + +- Case (A) is when at least one argument following the keyword is + on the same line as the keyword. +- Case (B) is the opposite (no arguments are on the same line as + the keyword). + +The possible values for this variable are keywords indicating how +to indent keyword invocation forms. + + `always-align' - Follow the same rules as `lisp-mode'. All + args are vertically aligned with the first arg in case (A), + and vertically aligned with the function name in case (B). + For instance: + (:require [foo.bar] + [bar.baz]) + (:require + [foo.bar] + [bar.baz]) + + `always-indent' - All args are indented like a macro body. + (:require [foo.bar] + [bar.baz]) + (:x + location + 0) + + `align-arguments' - Case (A) is indented like `lisp', and + case (B) is indented like a macro body. + (:require [foo.bar] + [bar.baz]) + (:x + location + 0)" + :safe #'symbolp + :type '(choice (const :tag "Same as `lisp-mode'" always-align) + (const :tag "Indent like a macro body" always-indent) + (const :tag "Indent like a macro body unless first arg is on the same line" + align-arguments)) + :package-version '(clojure-mode . "5.19.0")) + (defcustom clojure-use-backtracking-indent t "When non-nil, enable context sensitive indentation." :type 'boolean @@ -190,6 +236,7 @@ For example, \[ is allowed in :db/id[:db.part/user]." "shadow-cljs.edn" ; shadow-cljs "bb.edn" ; babashka "nbb.edn" ; nbb + "basilisp.edn" ; Basilisp (Python) ) "A list of files, which identify a Clojure project's root. Out-of-the box `clojure-mode' understands lein, boot, gradle, @@ -326,7 +373,8 @@ The prefixes are used to generate the correct namespace." (defvar clojure-mode-syntax-table (let ((table (make-syntax-table))) ;; Initialize ASCII charset as symbol syntax - (modify-syntax-entry '(0 . 127) "_" table) + ;; Control characters from 0-31 default to the punctuation syntax class + (modify-syntax-entry '(32 . 127) "_" table) ;; Word syntax (modify-syntax-entry '(?0 . ?9) "w" table) @@ -338,6 +386,7 @@ The prefixes are used to generate the correct namespace." (modify-syntax-entry ?\xa0 " " table) ; non-breaking space (modify-syntax-entry ?\t " " table) (modify-syntax-entry ?\f " " table) + (modify-syntax-entry ?\r " " table) ;; Setting commas as whitespace makes functions like `delete-trailing-whitespace' behave unexpectedly (#561) (modify-syntax-entry ?, "." table) @@ -493,16 +542,6 @@ ENDP and DELIM." "\\_<\\(?:'+\\|#\\)") (line-beginning-position))))) -(defconst clojure--collection-tag-regexp "#\\(::[a-zA-Z0-9._-]*\\|:?\\([a-zA-Z0-9._-]+/\\)?[a-zA-Z0-9._-]+\\)" - "Collection reader macro tag regexp. -It is intended to check for allowed strings that can come before a -collection literal (e.g. '[]' or '{}'), as reader macro tags. -This includes #fully.qualified/my-ns[:kw val] and #::my-ns{:kw -val} as of Clojure 1.9.") - -(make-obsolete-variable 'clojure--collection-tag-regexp nil "5.12.0") -(make-obsolete 'clojure-no-space-after-tag 'clojure-space-for-delimiter-p "5.12.0") - (declare-function paredit-open-curly "ext:paredit" t t) (declare-function paredit-close-curly "ext:paredit" t t) (declare-function paredit-convolute-sexp "ext:paredit") @@ -576,7 +615,7 @@ replacement for `cljr-expand-let`." (add-to-list 'imenu-generic-expression '(nil clojure-match-next-def 0)) (setq-local indent-tabs-mode nil) (setq-local paragraph-ignore-fill-prefix t) - (setq-local outline-regexp ";;;;* ") + (setq-local outline-regexp ";;;;* \\|(") ; comments and top-level forms (setq-local outline-level 'lisp-outline-level) (setq-local comment-start ";") (setq-local comment-start-skip ";+ *") @@ -1058,7 +1097,7 @@ any number of matches of `clojure--sym-forbidden-rest-chars'.")) 1 'clojure-character-face) ;; lambda arguments - %, %&, %1, %2, etc ;; must come after character literals for \% to be handled properly - ("\\<%[&1-9]?" (0 font-lock-variable-name-face)) + ("\\<%[&1-9]*" (0 font-lock-variable-name-face)) ;; namespace definitions: (ns foo.bar) (,(concat "(\\[ \r\n\t]*" ;; Possibly metadata, shorthand and/or longhand @@ -1072,12 +1111,13 @@ any number of matches of `clojure--sym-forbidden-rest-chars'.")) ;; keywords: {:oneword/ve/yCom|pLex.stu-ff 0} (,(concat "\\(:\\{1,2\\}\\)\\(" clojure--keyword-sym-regexp "?\\)\\(/\\)" "\\(" clojure--keyword-sym-regexp "\\)") + ;; with ns (1 'clojure-keyword-face) (2 font-lock-type-face) - ;; (2 'clojure-keyword-face) (3 'default) (4 'clojure-keyword-face)) - (,(concat "\\(:\\{1,2\\}\\)\\(" clojure--keyword-sym-regexp "\\)") + (,(concat "\\<\\(:\\{1,2\\}\\)\\(" clojure--keyword-sym-regexp "\\)") + ;; without ns (1 'clojure-keyword-face) (2 'clojure-keyword-face)) @@ -1232,7 +1272,7 @@ preceeded by a #." (clojure-string-start nil)))))) (defun clojure-font-lock-escaped-chars (bound) - "Highlight \escaped chars in strings. + "Highlight \\escaped chars in strings. BOUND denotes a buffer position to limit the search." (let ((found nil)) (while (and (not found) @@ -1468,7 +1508,7 @@ When called from lisp code align everything between BEG and END." (cl-incf count))) ;; Pre-indent the region to avoid aligning to improperly indented ;; contents (#551). Also fixes #360. - (indent-region (point) sexp-end) + (indent-region (point) (marker-position sexp-end)) (dotimes (_ count) (align-region (point) sexp-end nil `((clojure-align (regexp . clojure--search-whitespace-after-next-sexp) @@ -1652,6 +1692,15 @@ accepted by `clojure-indent-style'." ;; Car of form is not a symbol. (not (looking-at ".\\(?:\\sw\\|\\s_\\)")))) +(defcustom clojure-enable-indent-specs t + "Control whether to honor indent specs. +They can be either set via metadata on the function/macro, or via +`define-clojure-indent'. Set this to nil to get uniform +formatting of all forms." + :type 'boolean + :safe #'booleanp + :package-version '(clojure-mode . "5.19.0")) + ;; Check the general context, and provide indentation for data structures and ;; special macros. If current form is a function (or non-special macro), ;; delegate indentation to `clojure--normal-indent'. @@ -1685,7 +1734,8 @@ This function also returns nil meaning don't specify the indentation." (1+ (current-column)) ;; Function or macro call. (forward-char 1) - (let ((method (clojure--find-indent-spec)) + (let ((method (and clojure-enable-indent-specs + (clojure--find-indent-spec))) (last-sexp calculate-lisp-indent-last-sexp) (containing-form-column (1- (current-column)))) (pcase method @@ -1722,7 +1772,7 @@ This function also returns nil meaning don't specify the indentation." (cond ;; Preserve useful alignment of :require (and friends) in `ns' forms. ((and function (string-match "^:" function)) - (clojure--normal-indent last-sexp 'always-align)) + (clojure--normal-indent last-sexp clojure-indent-keyword-style)) ;; This should be identical to the :defn above. ((and function (string-match "\\`\\(?:\\S +/\\)?\\(def[a-z]*\\|with-\\)" @@ -1876,6 +1926,7 @@ work). To set it from Lisp code, use (deftest :defn) (are 2) (use-fixtures :defn) + (async 1) ;; core.logic (run :defn) @@ -2083,7 +2134,7 @@ content) are considered part of the preceding sexp." (defun clojure-sort-ns () "Internally sort each sexp inside the ns form." (interactive) - (comment-normalize-vars) + (comment-normalize-vars t) ;; `t`: avoid prompts (if (clojure-find-ns) (save-excursion (goto-char (match-beginning 0)) @@ -2205,11 +2256,11 @@ renaming a namespace." (defconst clojure-def-type-and-name-regex (concat "(\\(?:\\(?:\\sw\\|\\s_\\)+/\\)?" ;; Declaration - "\\(def\\(?:\\sw\\|\\s_\\)*\\)\\>" + "\\(def\\(?:\\sw\\|\\s_\\)*\\(?:-\\|\\>\\)\\)" ;; Any whitespace "[ \r\n\t]*" ;; Possibly type or metadata - "\\(?:#?^\\(?:{[^}]*}\\|\\(?:\\sw\\|\\s_\\)+\\)[ \r\n\t]*\\)*" + "\\(?:#?^\\(?:{[^}]*}+\\|\\(?:\\sw\\|\\s_\\)+\\)[ \r\n\t]*\\)*" ;; Symbol name "\\(\\(?:\\sw\\|\\s_\\)+\\)")) @@ -2229,7 +2280,7 @@ Returns a list pair, e.g. (\"defn\" \"abc\") or (\"deftest\" \"some-test\")." (defun clojure--looking-at-non-logical-sexp () "Return non-nil if text after point is \"non-logical\" sexp. \"Non-logical\" sexp are ^metadata and #reader.macros." - (comment-normalize-vars) + (comment-normalize-vars t) ;; `t`: avoid prompts (comment-forward (point-max)) (looking-at-p "\\(?:#?\\^\\)\\|#:?:?[[:alpha:]]")) @@ -3128,7 +3179,7 @@ Assumes cursor is at beginning of function." "Add an arity to a function. Assumes cursor is at beginning of function." - (let ((beg-line (what-line)) + (let ((beg-line (line-number-at-pos)) (end (save-excursion (forward-sexp) (point)))) (down-list 2) @@ -3140,7 +3191,7 @@ Assumes cursor is at beginning of function." (insert "[") (save-excursion (insert "])\n("))) ((looking-back "\\[" 1) ;; single-arity fn - (let* ((same-line (string= beg-line (what-line))) + (let* ((same-line (= beg-line (line-number-at-pos))) (new-arity-text (concat (when same-line "\n") "(["))) (save-excursion (goto-char end) @@ -3259,12 +3310,33 @@ With universal argument \\[universal-argument], act on the \"top-level\" form." \\{clojurec-mode-map}") +;;;###autoload +(define-derived-mode clojuredart-mode clojure-mode "ClojureDart" + "Major mode for editing Clojure Dart code. + +\\{clojuredart-mode-map}") + +;;;###autoload +(define-derived-mode jank-mode clojure-mode "Jank" + "Major mode for editing Jank code. + +\\{jank-mode-map}") + +;;;###autoload +(define-derived-mode joker-mode clojure-mode "Joker" + "Major mode for editing Joker code. + +\\{joker-mode-map}") + ;;;###autoload (progn (add-to-list 'auto-mode-alist - '("\\.\\(clj\\|cljd\\|dtm\\|edn\\)\\'" . clojure-mode)) + '("\\.\\(clj\\|cljd\\|dtm\\|edn\\|lpy\\)\\'" . clojure-mode)) (add-to-list 'auto-mode-alist '("\\.cljc\\'" . clojurec-mode)) (add-to-list 'auto-mode-alist '("\\.cljs\\'" . clojurescript-mode)) + (add-to-list 'auto-mode-alist '("\\.cljd\\'" . clojuredart-mode)) + (add-to-list 'auto-mode-alist '("\\.jank\\'" . jank-mode)) + (add-to-list 'auto-mode-alist '("\\.joke\\'" . joker-mode)) ;; boot build scripts are Clojure source files (add-to-list 'auto-mode-alist '("\\(?:build\\|profile\\)\\.boot\\'" . clojure-mode)) ;; babashka scripts are Clojure source files diff --git a/test/clojure-mode-bytecomp-warnings.el b/test/clojure-mode-bytecomp-warnings.el deleted file mode 100644 index 41b3230d..00000000 --- a/test/clojure-mode-bytecomp-warnings.el +++ /dev/null @@ -1,40 +0,0 @@ -;;; clojure-mode-bytecomp-warnings.el --- Check for byte-compilation problems -*- lexical-binding: t; -*- - -;; Copyright © 2012-2021 Bozhidar Batsov and contributors -;; -;; This program is free software: you can redistribute it and/or modify -;; it under the terms of the GNU General Public License as published by -;; the Free Software Foundation, either version 3 of the License, or -;; (at your option) any later version. - -;; This program is distributed in the hope that it will be useful, -;; but WITHOUT ANY WARRANTY; without even the implied warranty of -;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -;; GNU General Public License for more details. - -;; You should have received a copy of the GNU General Public License -;; along with this program. If not, see . - -;; This file is not part of GNU Emacs. - -;;; Commentary: - -;; This is a script to be loaded while visiting a `clojure-mode' source file. -;; It will prepare all requirements and then byte-compile the file and signal an -;; error on any warning. For example: -;; -;; emacs -Q --batch -l test/clojure-mode-bytecomp-warnings.el clojure-mode.el - -;; This assumes that all `clojure-mode' dependencies are already on the package -;; dir (probably from running `cask install'). - -(setq load-prefer-newer t) -(add-to-list 'load-path (expand-file-name "./")) -(require 'package) -(package-generate-autoloads 'clojure-mode default-directory) -(package-initialize) -(load-file "clojure-mode-autoloads.el") -(setq byte-compile-error-on-warn t) -(batch-byte-compile) - -;;; clojure-mode-bytecomp-warnings.el ends here diff --git a/test/clojure-mode-convert-collection-test.el b/test/clojure-mode-convert-collection-test.el index 28c5977e..14e52915 100644 --- a/test/clojure-mode-convert-collection-test.el +++ b/test/clojure-mode-convert-collection-test.el @@ -27,6 +27,7 @@ (require 'clojure-mode) (require 'buttercup) +(require 'test-helper "test/utils/test-helper") (describe "clojure-convert-collection-to-map" (when-refactoring-it "should convert a list to a map" diff --git a/test/clojure-mode-font-lock-test.el b/test/clojure-mode-font-lock-test.el index bb6ef74d..34771905 100644 --- a/test/clojure-mode-font-lock-test.el +++ b/test/clojure-mode-font-lock-test.el @@ -1,5 +1,4 @@ -;;; clojure-mode-font-lock-test.el --- Clojure Mode: Font lock test suite -;; -*- lexical-binding: t; -*- +;;; clojure-mode-font-lock-test.el --- Clojure Mode: Font lock test suite -*- lexical-binding: t; -*- ;; Copyright (C) 2014-2021 Bozhidar Batsov @@ -262,6 +261,13 @@ DESCRIPTION is the description of the spec." (9 10 nil) (11 16 nil)) + ("(colons:are:okay)" + (2 16 nil)) + + ("(some-ns/colons:are:okay)" + (2 8 font-lock-type-face) + (9 24 nil)) + ("(oneword/ve/yCom|pLex.stu-ff)" (2 8 font-lock-type-face) (9 10 nil) @@ -715,6 +721,19 @@ DESCRIPTION is the description of the spec." (10 10 default) (11 30 clojure-keyword-face))) + (when-fontifying-it "should handle keywords with colons" + (":a:a" + (1 4 clojure-keyword-face)) + + (":a:a/:a" + (1 7 clojure-keyword-face)) + + ("::a:a" + (1 5 clojure-keyword-face)) + + ("::a.a:a" + (1 7 clojure-keyword-face))) + (when-fontifying-it "should handle very complex keywords" (" :ve/yCom|pLex.stu-ff" (3 4 font-lock-type-face) @@ -824,7 +843,10 @@ DESCRIPTION is the description of the spec." (when-fontifying-it "should handle variables defined with def" ("(def foo 10)" (2 4 font-lock-keyword-face) - (6 8 font-lock-variable-name-face))) + (6 8 font-lock-variable-name-face)) + ("(def foo:bar 10)" + (2 4 font-lock-keyword-face) + (6 12 font-lock-variable-name-face))) (when-fontifying-it "should handle variables definitions of type string" ("(def foo \"hello\")" @@ -878,13 +900,24 @@ DESCRIPTION is the description of the spec." (2 3 font-lock-keyword-face) ( 5 7 font-lock-function-name-face))) - (when-fontifying-it "should handle lambda-params" + (when-fontifying-it "should handle lambda-params %, %1, %n..." ("#(+ % %2 %3 %&)" (5 5 font-lock-variable-name-face) (7 8 font-lock-variable-name-face) (10 11 font-lock-variable-name-face) (13 14 font-lock-variable-name-face))) + (when-fontifying-it "should handle multi-digit lambda-params" + ;; % args with >1 digit are rare and unidiomatic but legal up to + ;; `MAX_POSITIONAL_ARITY` in Clojure's compiler, which as of today is 20 + ("#(* %10 %15 %19 %20)" + ;; it would be better if this were just `font-lock-variable-name-face` but + ;; it seems to work as-is + (5 7 various-faces) + (9 11 font-lock-variable-name-face) + (13 15 font-lock-variable-name-face) + (17 19 various-faces))) + (when-fontifying-it "should handle nils" ("(= nil x)" (4 6 font-lock-constant-face)) diff --git a/test/clojure-mode-refactor-add-arity-test.el b/test/clojure-mode-refactor-add-arity-test.el index 9c75f128..5f1c5fb9 100644 --- a/test/clojure-mode-refactor-add-arity-test.el +++ b/test/clojure-mode-refactor-add-arity-test.el @@ -24,6 +24,7 @@ (require 'clojure-mode) (require 'buttercup) +(require 'test-helper "test/utils/test-helper") (describe "clojure-add-arity" diff --git a/test/clojure-mode-util-test.el b/test/clojure-mode-util-test.el index 565773d4..d905fc70 100644 --- a/test/clojure-mode-util-test.el +++ b/test/clojure-mode-util-test.el @@ -46,7 +46,7 @@ (bb-edn-src (expand-file-name "src" temp-dir))) (write-region "{}" nil bb-edn) (make-directory bb-edn-src) - (expect (clojure-project-dir bb-edn-src) + (expect (expand-file-name (clojure-project-dir bb-edn-src)) :to-equal (file-name-as-directory temp-dir)))))) (describe "clojure-project-relative-path" @@ -163,6 +163,11 @@ (with-clojure-buffer "(ns)(ns foo)" (expect (clojure-find-ns) :to-equal "foo")) (with-clojure-buffer "(ns )(ns foo)" + (expect (clojure-find-ns) :to-equal "foo"))) + (it "should ignore carriage returns" + (with-clojure-buffer "(ns \r\n foo)" + (expect (clojure-find-ns) :to-equal "foo")) + (with-clojure-buffer "(ns\r\n ^{:doc \"meta\r\n\"}\r\n foo\r\n)" (expect (clojure-find-ns) :to-equal "foo")))) (describe "clojure-sort-ns" @@ -326,6 +331,104 @@ {:nested (in|c x)})" (clojure-toggle-ignore-defun))) +(describe "clojure-find-def" + (it "should recognize def and defn" + (with-clojure-buffer-point + "(def foo 1)| + (defn bar [x y z] z)" + (expect (clojure-find-def) :to-equal '("def" "foo"))) + (with-clojure-buffer-point + "(def foo 1) + (defn bar |[x y z] z)" + (expect (clojure-find-def) :to-equal '("defn" "bar"))) + (with-clojure-buffer-point + "(def foo 1) + (defn ^:private bar |[x y z] z)" + (expect (clojure-find-def) :to-equal '("defn" "bar"))) + (with-clojure-buffer-point + "(defn |^{:doc \"A function\"} foo [] 1) + (defn ^:private bar 2)" + (expect (clojure-find-def) :to-equal '("defn" "foo")))) + (it "should recognize deftest, with or without metadata added to the var" + (with-clojure-buffer-point + "|(deftest ^{:a 1} simple-metadata) + (deftest ^{:a {}} complex-metadata) + (deftest no-metadata)" + (expect (clojure-find-def) :to-equal '("deftest" "simple-metadata"))) + (with-clojure-buffer-point + "(deftest ^{:a 1} |simple-metadata) + (deftest ^{:a {}} complex-metadata) + (deftest no-metadata)" + (expect (clojure-find-def) :to-equal '("deftest" "simple-metadata"))) + (with-clojure-buffer-point + "(deftest ^{:a 1} simple-metadata) + (deftest ^{:a {}} |complex-metadata) + (deftest no-metadata)" + (expect (clojure-find-def) :to-equal '("deftest" "complex-metadata"))) + (with-clojure-buffer-point + "(deftest ^{:a 1} simple-metadata) + (deftest ^{:|a {}} complex-metadata) + (deftest no-metadata)" + (expect (clojure-find-def) :to-equal '("deftest" "complex-metadata"))) + (with-clojure-buffer-point + "(deftest ^{:a 1} simple-metadata) + (deftest ^{:a {}} complex-metadata) + (deftest |no-metadata)" + (expect (clojure-find-def) :to-equal '("deftest" "no-metadata")))) + (it "should recognize defn-, with or without metadata" + (with-clojure-buffer-point + "(def foo 1) + (defn- bar |[x y z] z) + (def bar 2)" + (expect (clojure-find-def) :to-equal '("defn-" "bar"))) + (with-clojure-buffer-point + "(def foo 1) + (defn- ^:private bar |[x y z] z)" + (expect (clojure-find-def) :to-equal '("defn-" "bar"))) + (with-clojure-buffer-point + "(defn- |^{:doc \"A function\"} foo [] 1) + (defn- ^:private bar 2)" + (expect (clojure-find-def) :to-equal '("defn-" "foo"))) + (with-clojure-buffer-point + "(def foo 1) + (defn- ^{:|a {}} complex-metadata |[x y z] z) + (def bar 2)" + (expect (clojure-find-def) :to-equal '("defn-" "complex-metadata")))) + (it "should recognize def...-, with or without metadata" + (with-clojure-buffer-point + "(def foo 1) + (def- bar| 5) + (def baz 2)" + (expect (clojure-find-def) :to-equal '("def-" "bar"))) + (with-clojure-buffer-point + "(def foo 1) + (deftest- bar |[x y z] z) + (def baz 2)" + (expect (clojure-find-def) :to-equal '("deftest-" "bar"))) + (with-clojure-buffer-point + "(def foo 1) + (defxyz- bar| 5) + (def baz 2)" + (expect (clojure-find-def) :to-equal '("defxyz-" "bar"))) + (with-clojure-buffer-point + "(def foo 1) + (defn-n- bar| [x y z] z) + (def baz 2)" + (expect (clojure-find-def) :to-equal '("defn-n-" "bar"))) + (with-clojure-buffer-point + "(def foo 1) + (defn-n- ^:private bar |[x y z] z)" + (expect (clojure-find-def) :to-equal '("defn-n-" "bar"))) + (with-clojure-buffer-point + "(def-n- |^{:doc \"A function\"} foo [] 1) + (def- ^:private bar 2)" + (expect (clojure-find-def) :to-equal '("def-n-" "foo"))) + (with-clojure-buffer-point + "(def foo 1) + (defn-n- ^{:|a {}} complex-metadata |[x y z] z) + (def bar 2)" + (expect (clojure-find-def) :to-equal '("defn-n-" "complex-metadata"))))) + (provide 'clojure-mode-util-test) ;;; clojure-mode-util-test.el ends here diff --git a/test/test-checks.el b/test/test-checks.el deleted file mode 100644 index a4b4208f..00000000 --- a/test/test-checks.el +++ /dev/null @@ -1,30 +0,0 @@ -;; This is a script to be loaded from the root `clojure-mode' directory. It will -*- lexical-binding: t; -*- -;; prepare all requirements and then run `check-declare-directory' on -;; `default-directory'. For example: emacs -Q --batch -l test/test-checkdoc.el - -;; This assumes that all `clojure-mode' dependencies are already on the package -;; dir (probably from running `cask install'). - -(add-to-list 'load-path (expand-file-name "./")) -(require 'package) -(require 'check-declare) -(package-initialize) - -;; disable some annoying (or non-applicable) checkdoc checks -(setq checkdoc-package-keywords-flag nil) -(setq checkdoc-arguments-in-order-flag nil) -(setq checkdoc-verb-check-experimental-flag nil) - -(let ((files (directory-files default-directory t - "\\`[^.].*\\.el\\'" t))) - - ;; `checkdoc-file' was introduced in Emacs 25 - (when (fboundp 'checkdoc-file) - (dolist (file files) - (checkdoc-file file)) - (when (get-buffer "*Warnings*") - (message "Failing due to checkdoc warnings...") - (kill-emacs 1))) - - (when (apply #'check-declare-files files) - (kill-emacs 1))) diff --git a/test/utils/test-helper.el b/test/utils/test-helper.el index b359277c..af5273a2 100644 --- a/test/utils/test-helper.el +++ b/test/utils/test-helper.el @@ -25,13 +25,6 @@ (message "Running tests on Emacs %s" emacs-version) -(let* ((current-file (if load-in-progress load-file-name (buffer-file-name))) - (source-directory (locate-dominating-file current-file "Cask")) - ;; Do not load outdated byte code for tests - (load-prefer-newer t)) - ;; Load the file under test - (load (expand-file-name "clojure-mode" source-directory))) - (defmacro with-clojure-buffer (text &rest body) "Create a temporary buffer, insert TEXT, switch to clojure-mode and evaluate BODY." (declare (indent 1))