From: Stephen Leake <stephen_leake@stephe-leake.org>
To: emacs-devel <emacs-devel@gnu.org>
Subject: Re: installed packages long description.
Date: Thu, 13 Dec 2018 06:49:59 -0800 [thread overview]
Message-ID: <86mup9eb1k.fsf@stephe-leake.org> (raw)
In-Reply-To: <jwvk1kfy09q.fsf-monnier+gmane.emacs.devel@gnu.org> (Stefan Monnier's message of "Tue, 11 Dec 2018 21:02:30 -0500")
[-- Attachment #1: Type: text/plain, Size: 194 bytes --]
Stefan Monnier <monnier@iro.umontreal.ca> writes:
>> I'll submit a patch for review before committing anything.
>
> Thanks.
Attached. I'm not clear if this rates a NEWS entry?
--
-- Stephe
[-- Attachment #2: pkg-long-desc.diff --]
[-- Type: text/x-patch, Size: 9023 bytes --]
diff --git a/doc/lispref/package.texi b/doc/lispref/package.texi
index 37c1ee6697..730decc378 100644
--- a/doc/lispref/package.texi
+++ b/doc/lispref/package.texi
@@ -22,6 +22,7 @@ Packaging
* Simple Packages:: How to package a single .el file.
* Multi-file Packages:: How to package multiple files.
* Package Archives:: Maintaining package archives.
+* Archive Web Server:: Interfacing to an archive web server.
@end menu
@node Packaging Basics
@@ -249,7 +250,8 @@ Multi-file Packages
@end defun
If the content directory contains a file named @file{README}, this
-file is used as the long description.
+file is used as the long description (overriding any @samp{;;;
+Commentary:} section).
If the content directory contains a file named @file{dir}, this is
assumed to be an Info directory file made with @command{install-info}.
@@ -311,8 +313,8 @@ Package Archives
A package archive is simply a directory in which the package files,
and associated files, are stored. If you want the archive to be
-reachable via HTTP, this directory must be accessible to a web server.
-How to accomplish this is beyond the scope of this manual.
+reachable via HTTP, this directory must be accessible to a web server;
+@xref{Archive Web Server}.
A convenient way to set up and update a package archive is via the
@code{package-x} library. This is included with Emacs, but not loaded
@@ -393,3 +395,28 @@ Package Archives
@pxref{Top,, GnuPG, gnupg, The GNU Privacy Guard Manual}. Emacs comes
with an interface to GNU Privacy Guard, @pxref{Top,, EasyPG, epa,
Emacs EasyPG Assistant Manual}.
+
+@node Archive Web Server
+@section Interfacing to an archive web server
+@cindex archive web server
+
+A web server providing access to a package archive must support the
+following queries:
+
+@table @asis
+@item archive-contents
+Return a lisp form describing the archive contents. The form is a list
+of 'package-desc' structures (see @file{package.el}), except the first
+element of the list is the archive version.
+
+@item <package name>-readme.txt
+Return the long description of the package.
+
+@item <file name>.sig
+Return the signature for the file.
+
+@item <file name>
+Return the file. This will be the tarball for a multi-file
+package, or the single file for a simple package.
+
+@end table
diff --git a/lisp/emacs-lisp/package.el b/lisp/emacs-lisp/package.el
index dcede1a5b2..1752c7e9fe 100644
--- a/lisp/emacs-lisp/package.el
+++ b/lisp/emacs-lisp/package.el
@@ -2123,6 +2123,9 @@ package-delete
(add-hook 'post-command-hook #'package-menu--post-refresh)
(delete-directory dir t)
;; Remove NAME-VERSION.signed and NAME-readme.txt files.
+ ;;
+ ;; NAME-readme.txt files are no longer created, but they
+ ;; may be left around from an earlier install.
(dolist (suffix '(".signed" "readme.txt"))
(let* ((version (package-version-join (package-desc-version pkg-desc)))
(file (concat (if (string= suffix ".signed")
@@ -2233,6 +2236,45 @@ package--print-help-section
(declare-function lm-commentary "lisp-mnt" (&optional file))
+(defun package--get-description (desc)
+ "Return a string containing the long description of the package DESC.
+The description is read from the installed package files."
+ ;; Installed packages have nil for kind, so we look for README
+ ;; first, then fall back to the Commentary header.
+
+ ;; We don’t include README.md here, because that is often the home
+ ;; page on a site like github, and not suitable as the package long
+ ;; description.
+ (let ((files '("README-elpa" "README-elpa.md" "README" "README.rst" "README.org"))
+ file
+ (srcdir (package-desc-dir desc))
+ result)
+ (while (and files
+ (not result))
+ (setq file (pop files))
+ (when (file-readable-p (expand-file-name file srcdir))
+ ;; Found a README.
+ (with-temp-buffer
+ (insert-file-contents (expand-file-name file srcdir))
+ (setq result (buffer-string)))))
+
+ (or
+ result
+
+ ;; Look for Commentary header.
+ (let ((mainsrcfile (expand-file-name (format "%s.el" (package-desc-name desc))
+ srcdir)))
+ (when (file-readable-p mainsrcfile)
+ (with-temp-buffer
+ (insert (or (lm-commentary mainsrcfile) ""))
+ (goto-char (point-min))
+ (when (re-search-forward "^;;; Commentary:\n" nil t)
+ (replace-match ""))
+ (while (re-search-forward "^\\(;+ ?\\)" nil t)
+ (replace-match ""))
+ (buffer-string))))
+ )))
+
(defun describe-package-1 (pkg)
(require 'lisp-mnt)
(let* ((desc (or
@@ -2406,7 +2448,8 @@ describe-package-1
(insert "\n")
(if built-in
- ;; For built-in packages, insert the commentary.
+ ;; For built-in packages, get the description from the
+ ;; Commentary header.
(let ((fn (locate-file (format "%s.el" name) load-path
load-file-rep-suffixes))
(opoint (point)))
@@ -2417,27 +2460,25 @@ describe-package-1
(replace-match ""))
(while (re-search-forward "^\\(;+ ?\\)" nil t)
(replace-match ""))))
- (let* ((basename (format "%s-readme.txt" name))
- (readme (expand-file-name basename package-user-dir))
- readme-string)
- ;; For elpa packages, try downloading the commentary. If that
- ;; fails, try an existing readme file in `package-user-dir'.
- (cond ((and (package-desc-archive desc)
- (package--with-response-buffer (package-archive-base desc)
- :file basename :noerror t
- (save-excursion
- (goto-char (point-max))
- (unless (bolp)
- (insert ?\n)))
- (write-region nil nil
- (expand-file-name readme package-user-dir)
- nil 'silent)
- (setq readme-string (buffer-string))
- t))
- (insert readme-string))
- ((file-readable-p readme)
- (insert-file-contents readme)
- (goto-char (point-max))))))))
+
+ (if (package-installed-p desc)
+ ;; For installed packages, get the description from the installed files.
+ (insert (package--get-description desc))
+
+ ;; For non-built-in, non-installed packages, get description from the archive.
+ (let* ((basename (format "%s-readme.txt" name))
+ readme-string)
+
+ (package--with-response-buffer (package-archive-base desc)
+ :file basename :noerror t
+ (save-excursion
+ (goto-char (point-max))
+ (unless (bolp)
+ (insert ?\n)))
+ (setq readme-string (buffer-string))
+ t)
+ (insert readme-string))
+ ))))
(defun package-install-button-action (button)
(let ((pkg-desc (button-get button 'package-desc)))
diff --git a/test/lisp/emacs-lisp/package-tests.el b/test/lisp/emacs-lisp/package-tests.el
index f08bc92ff2..17431f31f8 100644
--- a/test/lisp/emacs-lisp/package-tests.el
+++ b/test/lisp/emacs-lisp/package-tests.el
@@ -435,11 +435,24 @@ package-test-desc-version-string
(save-excursion (should (search-forward "Summary: A single-file package with no dependencies" nil t)))
(save-excursion (should (search-forward "Homepage: http://doodles.au" nil t)))
(save-excursion (should (re-search-forward "Keywords: \\[?frobnicate\\]?" nil t)))
- ;; No description, though. Because at this point we don't know
- ;; what archive the package originated from, and we don't have
- ;; its readme file saved.
+ (save-excursion (should (search-forward "This package provides a minor mode to frobnicate"
+ nil t)))
)))
+(ert-deftest package-test-describe-installed-multi-file-package ()
+ "Test displaying of the readme for installed multi-file package."
+
+ (with-package-test ()
+ (package-initialize)
+ (package-refresh-contents)
+ (package-install 'multi-file)
+ (with-fake-help-buffer
+ (describe-package 'multi-file)
+ (goto-char (point-min))
+ (should (search-forward "Homepage: http://puddles.li" nil t))
+ (should (search-forward "This is a bare-bones readme file for the multi-file"
+ nil t)))))
+
(ert-deftest package-test-describe-non-installed-package ()
"Test displaying of the readme for non-installed package."
next prev parent reply other threads:[~2018-12-13 14:49 UTC|newest]
Thread overview: 11+ messages / expand[flat|nested] mbox.gz Atom feed top
2018-12-05 1:39 installed packages long description Stephen Leake
2018-12-09 16:38 ` Stefan Monnier
2018-12-09 18:46 ` Stephen Leake
2018-12-10 2:40 ` Stefan Monnier
2018-12-10 19:27 ` Stephen Leake
2018-12-11 20:01 ` Stefan Monnier
2018-12-12 1:46 ` Stephen Leake
2018-12-12 2:02 ` Stefan Monnier
2018-12-13 14:49 ` Stephen Leake [this message]
2018-12-13 15:24 ` Stefan Monnier
2018-12-13 22:47 ` Stephen Leake
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=86mup9eb1k.fsf@stephe-leake.org \
--to=stephen_leake@stephe-leake.org \
--cc=emacs-devel@gnu.org \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
Code repositories for project(s) associated with this external index
https://git.savannah.gnu.org/cgit/emacs.git
https://git.savannah.gnu.org/cgit/emacs/org-mode.git
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.