branch: elpa/gptel
commit 7218aedd6f8294af5be876c0c18a733863156b7b
Author: Karthik Chikmagalur <karthikchikmaga...@gmail.com>
Commit: Karthik Chikmagalur <karthikchikmaga...@gmail.com>

    gptel: Enforce uniform convention for calling  presets
    
    * gptel.el (gptel--apply-preset, gptel--preset-syms,
    gptel-with-preset, gptel--transform-apply-preset): Ensure that the
    preset-related functions `gptel--apply-preset',
    `gptel--preset-syms' and the macro `gptel-with-preset' all refer
    to presets the same way: A preset can be passed to these by name
    or as a (possibly anonymous) preset spec, a plist.  Previously
    they each had different conventions for their preset argument.
    
    All of these are now valid:
    
      ;; Refer to preset by name
      (gptel--apply-preset 'websearch)
      (gptel--preset-syms  'websearch)
      (gptel-with-preset   'websearch)
    
      ;; Refer to preset by full spec
      (gptel--apply-preset '(:tools ... :stream nil))
      (gptel--preset-syms  '(:tools ... :stream nil))
      (gptel-with-preset   '(:tools ... :stream nil))
    
    Note that `gptel-with-preset' now evaluates its PRESET argument
    and it must be quoted as above.
    
    * gptel-transient.el (gptel--preset): Adjust for preset API
    changes.
---
 gptel-transient.el |  5 ++---
 gptel.el           | 50 ++++++++++++++++++++++++++------------------------
 2 files changed, 28 insertions(+), 27 deletions(-)

diff --git a/gptel-transient.el b/gptel-transient.el
index 5b0da5b838..f4f93b1c50 100644
--- a/gptel-transient.el
+++ b/gptel-transient.el
@@ -935,10 +935,9 @@ together.  See `gptel-make-preset' for details."
         `(lambda () (interactive)
            (gptel--set-with-scope 'gptel--preset ',name-sym
             gptel--set-buffer-locally)
-           (gptel--apply-preset
-            ',(cons name-sym preset)
+           (gptel--apply-preset ',preset
             (lambda (sym val) (gptel--set-with-scope
-                               sym val gptel--set-buffer-locally)))
+                          sym val gptel--set-buffer-locally)))
            (message "Applied gptel preset %s"
             (propertize ,name 'face 'transient-value))
            (when transient--stack
diff --git a/gptel.el b/gptel.el
index 72cf538ef7..0a0db05740 100644
--- a/gptel.el
+++ b/gptel.el
@@ -3686,8 +3686,8 @@ kill-ring."
 (defun gptel--apply-preset (preset &optional setter)
   "Apply gptel PRESET with SETTER.
 
-PRESET is the name of a preset, or a spec of the form
- (NAME :KEY1 VAL1 :KEY2 VAL2 ...).
+PRESET is the name of a preset, or a spec (plist) of the form
+ (:KEY1 VAL1 :KEY2 VAL2 ...).
 
 SETTER is the function used to set the gptel options.  It must accept
 two arguments, the symbol being set and the value to set it to.  It
@@ -3697,10 +3697,10 @@ example) apply the preset buffer-locally."
     (let ((spec (or (gptel-get-preset preset)
                     (user-error "gptel preset \"%s\": Cannot find preset."
                                 preset))))
-      (setq preset (cons preset spec))))
+      (setq preset spec)))
   (unless setter (setq setter #'set))
-  (when-let* ((func (plist-get (cdr preset) :pre))) (funcall func))
-  (when-let* ((parents (plist-get (cdr preset) :parents)))
+  (when-let* ((func (plist-get preset :pre))) (funcall func))
+  (when-let* ((parents (plist-get preset :parents)))
     (mapc #'gptel--apply-preset (ensure-list parents)))
   (map-do
    (lambda (key val)
@@ -3712,16 +3712,14 @@ example) apply the preset buffer-locally."
           (if (and (symbolp val) (not (functionp val)))
               (if-let* ((directive (alist-get val gptel-directives)))
                   (funcall setter sym directive)
-                (user-error "gptel preset \"%s\": Cannot find directive %s"
-                            (car preset) val))
+                (user-error "gptel preset: Cannot find directive %s" val))
             (funcall setter sym val))))
        (:backend
         (setq val (cl-etypecase val
                     (gptel-backend val)
                     (string (gptel-get-backend val))))
         (unless val
-          (user-error "gptel preset \"%s\": Cannot find backend %s."
-                      (car preset) val))
+          (user-error "gptel preset: Cannot find backend %s." val))
         (funcall setter 'gptel-backend val))
        (:tools                          ;TEMP Confirm this `:append' convention
         (let* ((append (when (eq (car-safe val) :append) (setq val (cdr val)) 
t))
@@ -3733,8 +3731,7 @@ example) apply the preset buffer-locally."
                                        (string (ignore-errors
                                                  (gptel-get-tool tool-name))))
                           do (unless tool
-                               (user-error "gptel preset \"%s\": Cannot find 
tool %s."
-                                           (car preset) val))
+                               (user-error "gptel preset: Cannot find tool 
%s." val))
                           collect tool))))
           (funcall setter 'gptel-tools ;append makes a copy of gptel-tools, 
intentional
                    (if append (delete-dups (append gptel-tools tools)) 
tools))))
@@ -3746,15 +3743,20 @@ example) apply the preset buffer-locally."
         (funcall setter sym val))
        (_ (display-warning
            '(gptel presets)
-           (format "gptel preset \"%s\": setting for %s not found, ignoring."
-                   (car preset) key)))))
-   (cdr preset))
-  (when-let* ((func (plist-get (cdr preset) :post))) (funcall func)))
+           (format "gptel preset: setting for %s not found, ignoring." key)))))
+   preset)
+  (when-let* ((func (plist-get preset :post))) (funcall func)))
 
 (defun gptel--preset-syms (preset)
   "Return a list of gptel variables (symbols) set by PRESET.
 
-PRESET is a spec (plist) of keys and values."
+PRESET is the name of a preset, or a spec (plist) of the form
+ (:KEY1 VAL1 :KEY2 VAL2 ...)."
+  (when (memq (type-of preset) '(string symbol))
+    (let ((spec (or (gptel-get-preset preset)
+                    (user-error "gptel preset \"%s\": Cannot find preset."
+                                preset))))
+      (setq preset spec)))
   (let* ((index preset)
          syms key val)
     (while index
@@ -3782,14 +3784,14 @@ PRESET is a spec (plist) of keys and values."
   "Run BODY with gptel preset NAME applied.
 
 This macro can be used to create `gptel-request' command with settings
-from a gptel preset applied.  NAME is the preset name, typically a
-symbol."
+from a gptel preset applied.
+
+NAME is the name of a preset, or a spec (plist) of the form
+ (:KEY1 VAL1 :KEY2 VAL2 ...).  It must be quoted."
   (declare (indent 1))
-  `(cl-progv (gptel--preset-syms
-              (gptel-get-preset ,(if (symbolp name) `',name name)))
-       nil
-     (gptel--apply-preset ,(if (symbolp name) `',name name))
-     ,@body))
+  `(cl-progv (gptel--preset-syms ,name) nil
+    (gptel--apply-preset ,name)
+    ,@body))
 
 ;;;; Presets in-buffer UI
 (defun gptel--transform-apply-preset (_fsm)
@@ -3807,7 +3809,7 @@ If the user prompt begins with @foo, the preset foo is 
applied."
                     (preset (or (gptel-get-preset (intern-soft name))
                                 (gptel-get-preset name))))
           (delete-region (match-beginning 0) (match-end 0))
-          (gptel--apply-preset (cons name preset)
+          (gptel--apply-preset preset
                                (lambda (sym val)
                                  (set (make-local-variable sym) val))))))))
 

Reply via email to