* lisp/ob-tangle.el: (org-babel-tangle-collect-blocks): source blocks without a language are not ignored anymore, if they inherit a src-tfile other than "yes" or "no". * lisp/ob-core.el: adapts the org-babel-src-block-regexp regular expression to make the language part of a source block optional. * testing/lisp/test-ob-tangle.el: (ob-tangle/collect-blocks): Augment the test with source blocks without language specifiers. * etc/ORG-NEWS: (=ob-tangle= now tangles source blocks that do not specify a =language= if an inherited property sets a tangle filename): Document the new behaviour. * doc/org-manual.org: (Structure of Code Blocks) Clarify what happens when the language identifier is omitted.
TINYCHANGE --- Here the same patch with the TINYCHANGE cookie. I'll get the fsf papers anyway as I intend to commit more. Thanks Ihor. doc/org-manual.org | 3 ++- etc/ORG-NEWS | 8 ++++++++ lisp/ob-core.el | 4 ++-- lisp/ob-tangle.el | 8 ++++++-- testing/lisp/test-ob-tangle.el | 16 ++++++++++++---- 5 files changed, 30 insertions(+), 9 deletions(-) diff --git a/doc/org-manual.org b/doc/org-manual.org index 2d5fd57b3..f0c53265a 100644 --- a/doc/org-manual.org +++ b/doc/org-manual.org @@ -18028,7 +18028,8 @@ or block. See [[*Languages]], for identifiers of supported languages. When =<language>= identifier is omitted, the block also cannot - have =<switches>= and =<header arguments>=. + have =<switches>= and =<header arguments>=. Otherwise, the first + switch/argument will be treated as =<language>=. Language identifier is also used to fontify code blocks in Org buffers, when ~org-src-fontify-natively~ is set to non-~nil~. See diff --git a/etc/ORG-NEWS b/etc/ORG-NEWS index 2d4616fab..4aa628c7e 100644 --- a/etc/ORG-NEWS +++ b/etc/ORG-NEWS @@ -437,6 +437,14 @@ For example, given =H:3= and =toc:2= in =#+OPTIONS:=, all headings at the 1st and 2nd level appear in the table of contents and those at the 3rd level do not. +*** =ob-tangle= now tangles source blocks that do not specify a =language= if an inherited property sets a tangle filename + +Previously, all source blocks that did not specify a =language= where +ignored by ~org-babel-tangle-collect-blocks~. Now, if it inherits a +:tangle header argument with a value other than =no= or =yes= (that is, a +filename), a source block without =language= will get tangled to that +file. + * Version 9.7 ** Important announcements and breaking changes diff --git a/lisp/ob-core.el b/lisp/ob-core.el index ff021cbd3..cf56367f8 100644 --- a/lisp/ob-core.el +++ b/lisp/ob-core.el @@ -216,8 +216,8 @@ When matching, reference is stored in match group 1." (defvar org-babel-src-block-regexp (concat - ;; (1) indentation (2) lang - "^\\([ \t]*\\)#\\+begin_src[ \t]+\\([^ \f\t\n\r\v]+\\)[ \t]*" + ;; (1) indentation (2) lang + "^\\([ \t]*\\)#\\+begin_src\\(?:[ \t]+\\([^ \f\t\n\r\v]*\\)\\)?[ \t]*" ;; (3) switches "\\([^\":\n]*\"[^\"\n*]*\"[^\":\n]*\\|[^\":\n]*\\)" ;; (4) header arguments diff --git a/lisp/ob-tangle.el b/lisp/ob-tangle.el index 044212da2..d37d3c67f 100644 --- a/lisp/ob-tangle.el +++ b/lisp/ob-tangle.el @@ -508,9 +508,13 @@ code blocks by target file." (src-lang (nth 0 info)) (src-tfile (cdr (assq :tangle (nth 2 info))))) (unless (or (string= src-tfile "no") - (not src-lang) ;; src block without lang + ;; src block without lang + (and (not src-lang) (string= src-tfile "yes")) (and tangle-file (not (equal tangle-file src-tfile))) - (and lang-re (not (string-match-p lang-re src-lang)))) + ;; lang-re but either no lang or lang doesn't match + (and lang-re + (or (not src-lang) + (not (string-match-p lang-re src-lang))))) ;; Add the spec for this block to blocks under its tangled ;; file name. (let* ((block (org-babel-tangle-single-block counter)) diff --git a/testing/lisp/test-ob-tangle.el b/testing/lisp/test-ob-tangle.el index e13bca0cb..6e95c4c91 100644 --- a/testing/lisp/test-ob-tangle.el +++ b/testing/lisp/test-ob-tangle.el @@ -628,6 +628,10 @@ another block \"H1: :tangle ~/../../tmp/absolute.el\" #+end_src +#+begin_src +\"H1: no language and inherited :tangle relative.el in properties\" +#+end_src + * H2 without :tangle in properties #+begin_src emacs-lisp @@ -660,6 +664,10 @@ another block #+begin_src emacs-lisp :tangle ~/../../tmp/absolute.el \"H2: :tangle ~/../../tmp/absolute.el\" +#+end_src + +#+begin_src +\"H2: without language and thus without :tangle\" #+end_src" `((?a . ,el-file-abs) (?r . ,el-file-rel)))) @@ -684,7 +692,7 @@ another block collected-blocks))))) (should (equal (funcall normalize-expected-targets-alist `(("/tmp/absolute.el" . 4) - ("relative.el" . 5) + ("relative.el" . 6) ;; file name differs between tests (,el-file-abs . 4))) (funcall count-blocks-in-target-files @@ -699,11 +707,11 @@ another block (should (equal (funcall normalize-expected-targets-alist `(("/tmp/absolute.el" . 4) - ("relative.el" . 5) + ("relative.el" . 6) ;; Default :tangle header now also ;; points to the file name derived from the name of - ;; the Org file, so 5 blocks should go there. - (,el-file-abs . 5))) + ;; the Org file, so 6 blocks should go there. + (,el-file-abs . 6))) (funcall count-blocks-in-target-files (org-babel-tangle-collect-blocks))))))))) -- 2.47.1