pierre.techouey...@free.fr (Pierre Téchoueyres) writes:

Hello,
> ...
>> ...
>> Is it really an Org problem? E.g., couldn't you put a coding: cookie in
>> your ".cmd" file? IMO, the coding system depends on the includee, not
>> the includer.
>
> I tend to aggree with you that TRTDT is to put cookies or something
> inside the included file. But :
>   a) This seem to not work as expected (see exemples joinned).
>   b) Sometimes you can't modify the included file (ex: remote file access).
> ...
> For a I can try to jump into the rabbit hole and find a solution (but
>  for now I'm lost)

I did my homework : found a fix for a) and rebased previous patch on master.

Regards,

>From 679fa184dff97f1a5ff617144dc7d87e95b8ccd9 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Pierre=20T=C3=A9choueyres?= <pierre.techouey...@free.fr>
Date: Sat, 21 Apr 2018 00:31:10 +0200
Subject: [PATCH] Add new keyword :coding for #+include directive

* lisp/ox.el (org-export-expand-include-keyword): Add new keyword
  `:coding' for specify the file encoding whith the `#+include:'
  directive.

This allow to use somting like :
  #+include: "./myfile" :coding cp850-dos
when your org-file is encoded in utf-8 for example.
---
 etc/ORG-NEWS |   7 ++++
 lisp/ox.el   | 121 +++++++++++++++++++++++++++++++----------------------------
 2 files changed, 71 insertions(+), 57 deletions(-)

diff --git a/etc/ORG-NEWS b/etc/ORG-NEWS
index abebe08fe..8b717d8f3 100644
--- a/etc/ORG-NEWS
+++ b/etc/ORG-NEWS
@@ -121,6 +121,13 @@ now sort according to the locale’s collation rules instead of by
 code-point.
 
 ** New features
+*** New keyword for ~#+include:~ directive
+Add ~:coding "codign-system"~ keyword to allow include of files from
+different codign system than the main org-file.
+For example:
+#+begin_example
+,#+INCLUDE: "myfile.cmd" src cmd :coding cp850-dos
+#+end_example
 *** Add ~:results link~ support for Babel
 
 With this output format, create a link to the file specified in
diff --git a/lisp/ox.el b/lisp/ox.el
index 5a83ae01d..e75030ffb 100644
--- a/lisp/ox.el
+++ b/lisp/ox.el
@@ -3298,6 +3298,12 @@ storing and resolving footnotes.  It is created automatically."
 				  (org-unbracket-string "\"" "\"" matched)
 				  dir)))
 			   (setq value (replace-match "" nil nil value)))))
+		   (coding
+		    (intern (or (and (string-match
+				      ":coding +\\<\\([a-z0-9\\-]+\\)\\>" value)
+				     (prog1 (match-string 1 value)
+				       (setq value (replace-match "" nil nil value))))
+				(symbol-name coding-system-for-read))))
 		   (only-contents
 		    (and (string-match ":only-contents *\\([^: \r\t\n]\\S-*\\)?"
 				       value)
@@ -3331,65 +3337,66 @@ storing and resolving footnotes.  It is created automatically."
 			       (match-string 1 value))))
 	      ;; Remove keyword.
 	      (delete-region (point) (line-beginning-position 2))
-	      (cond
-	       ((not file) nil)
-	       ((not (file-readable-p file))
-		(error "Cannot include file %s" file))
-	       ;; Check if files has already been parsed.  Look after
-	       ;; inclusion lines too, as different parts of the same
-	       ;; file can be included too.
-	       ((member (list file lines) included)
-		(error "Recursive file inclusion: %s" file))
-	       (t
+	      (let ((coding-system-for-read coding))
 		(cond
-		 ((eq env 'literal)
-		  (insert
-		   (let ((ind-str (make-string ind ?\s))
-			 (arg-str (if (stringp args) (format " %s" args) ""))
-			 (contents
-			  (org-escape-code-in-string
-			   (org-export--prepare-file-contents file lines))))
-		     (format "%s#+BEGIN_%s%s\n%s%s#+END_%s\n"
-			     ind-str block arg-str contents ind-str block))))
-		 ((stringp block)
-		  (insert
-		   (let ((ind-str (make-string ind ?\s))
-			 (contents
-			  (org-export--prepare-file-contents file lines)))
-		     (format "%s#+BEGIN_%s\n%s%s#+END_%s\n"
-			     ind-str block contents ind-str block))))
+		 ((not file) nil)
+		 ((not (file-readable-p file))
+		  (error "Cannot include file %s" file))
+		 ;; Check if files has already been parsed.  Look after
+		 ;; inclusion lines too, as different parts of the same
+		 ;; file can be included too.
+		 ((member (list file lines) included)
+		  (error "Recursive file inclusion: %s" file))
 		 (t
-		  (insert
-		   (with-temp-buffer
-		     (let ((org-inhibit-startup t)
-			   (lines
-			    (if location
-				(org-export--inclusion-absolute-lines
-				 file location only-contents lines)
-			      lines)))
-		       (org-mode)
-		       (insert
-			(org-export--prepare-file-contents
-			 file lines ind minlevel
-			 (or (gethash file file-prefix)
-			     (puthash file
-				      (cl-incf current-prefix)
-				      file-prefix))
-			 footnotes
-			 includer-file)))
-		     (org-export-expand-include-keyword
-		      (cons (list file lines) included)
-		      (file-name-directory file)
-		      footnotes)
-		     (buffer-string)))))
-		;; Expand footnotes after all files have been
-		;; included.  Footnotes are stored at end of buffer.
-		(unless included
-		  (org-with-wide-buffer
-		   (goto-char (point-max))
-		   (maphash (lambda (k v)
-			      (insert (format "\n[fn:%s] %s\n" k v)))
-			    footnotes))))))))))))
+		  (cond
+		   ((eq env 'literal)
+		    (insert
+		     (let ((ind-str (make-string ind ?\s))
+			   (arg-str (if (stringp args) (format " %s" args) ""))
+			   (contents
+			    (org-escape-code-in-string
+			     (org-export--prepare-file-contents file lines))))
+		       (format "%s#+BEGIN_%s%s\n%s%s#+END_%s\n"
+			       ind-str block arg-str contents ind-str block))))
+		   ((stringp block)
+		    (insert
+		     (let ((ind-str (make-string ind ?\s))
+			   (contents
+			    (org-export--prepare-file-contents file lines)))
+		       (format "%s#+BEGIN_%s\n%s%s#+END_%s\n"
+			       ind-str block contents ind-str block))))
+		   (t
+		    (insert
+		     (with-temp-buffer
+		       (let ((org-inhibit-startup t)
+			     (lines
+			      (if location
+				  (org-export--inclusion-absolute-lines
+				   file location only-contents lines)
+				lines)))
+			 (org-mode)
+			 (insert
+			  (org-export--prepare-file-contents
+			   file lines ind minlevel
+			   (or (gethash file file-prefix)
+			       (puthash file
+					(cl-incf current-prefix)
+					file-prefix))
+			   footnotes
+			   includer-file)))
+		       (org-export-expand-include-keyword
+			(cons (list file lines) included)
+			(file-name-directory file)
+			footnotes)
+		       (buffer-string)))))
+		  ;; Expand footnotes after all files have been
+		  ;; included.  Footnotes are stored at end of buffer.
+		  (unless included
+		    (org-with-wide-buffer
+		     (goto-char (point-max))
+		     (maphash (lambda (k v)
+				(insert (format "\n[fn:%s] %s\n" k v)))
+			      footnotes)))))))))))))
 
 (defun org-export--inclusion-absolute-lines (file location only-contents lines)
   "Resolve absolute lines for an included file with file-link.
-- 
2.14.3

>From fbd854f566d47729f7dcc0f304b537890a6eec0c Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Pierre=20T=C3=A9choueyres?= <pierre.techouey...@free.fr>
Date: Sat, 21 Apr 2018 00:19:10 +0200
Subject: [PATCH] Correctly convert encoding of included files

* lisp/ox.el (org-export--prepare-file-contents): convert temporary
  buffer encoding to org buffer's encoding.
---
 lisp/ox.el | 5 ++++-
 1 file changed, 4 insertions(+), 1 deletion(-)

diff --git a/lisp/ox.el b/lisp/ox.el
index 5a83ae01d..a41d4d8d0 100644
--- a/lisp/ox.el
+++ b/lisp/ox.el
@@ -3481,7 +3481,10 @@ the included document.
 Optional argument INCLUDER is the file name where the inclusion
 is to happen."
   (with-temp-buffer
-    (insert-file-contents file)
+    (let ((org-buffer-coding-system buffer-file-coding-system))
+      (insert-file-contents file)
+      (unless (eq org-buffer-coding-system buffer-file-coding-system)
+	(set-buffer-file-coding-system org-buffer-coding-system)))
     (when lines
       (let* ((lines (split-string lines "-"))
 	     (lbeg (string-to-number (car lines)))
-- 
2.14.3

Reply via email to