aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--sx-cache.el25
-rw-r--r--sx-favorites.el32
-rw-r--r--sx-networks.el36
-rw-r--r--sx-question-list.el64
-rw-r--r--sx-question-mode.el2
5 files changed, 98 insertions, 61 deletions
diff --git a/sx-cache.el b/sx-cache.el
index e3b356b..a564a53 100644
--- a/sx-cache.el
+++ b/sx-cache.el
@@ -67,6 +67,31 @@ DATA will be written as returned by `prin1'."
(sx-cache-get-file-name cache))
data)
+(defun sx-cache--invalidate (cache &optional vars init-method)
+ "Set cache CACHE to nil.
+
+VARS is a list of variables to unbind to ensure cache is cleared.
+If INIT-METHOD is defined, call it after all invalidation to
+re-initialize the cache."
+ (sx-cache-set cache nil)
+ (mapc #'makunbound vars)
+ (funcall init-method))
+
+(defun sx-cache-invalidate-all (&optional save-auth)
+ "Invalidate all caches using `sx-cache--invalidate'.
+
+Afterwards reinitialize caches using `sx-initialize'.
+
+If SAVE-AUTH is non-nil, do not clear AUTH cache."
+ (let ((caches (let ((default-directory sx-cache-directory))
+ (file-expand-wildcards "*.el"))))
+ (when save-auth
+ (setq caches (cl-remove-if (lambda (x)
+ (string= x "auth.el")) caches)))
+ (lwarn 'stack-mode :debug "Invalidating: %S" caches)
+ (mapc #'sx-cache--invalidate caches)
+ (sx-initialize 'force)))
+
(provide 'sx-cache)
;;; sx-cache.el ends here
diff --git a/sx-favorites.el b/sx-favorites.el
index 9412b5b..3aa96dd 100644
--- a/sx-favorites.el
+++ b/sx-favorites.el
@@ -43,16 +43,15 @@
Each element has the form (SITE FAVORITE-LIST). And each element
in FAVORITE-LIST is the numerical QUESTION_ID.")
-(defun sx-favorites--ensure-favorite-list ()
- (unless sx-favorites--user-favorite-list
- (setq sx-favorites--user-favorite-list
- (sx-cache-get
- 'question-favorites
- (let ((sites
- (mapcar (lambda (site)
- `(,site))
- sx-network--user-sites)))
- `(quote ,sites))))))
+(defun sx-favorites--initialize ()
+ "Ensure question-favorites cache is available.
+
+Added as hook to initialization."
+ (or (setq sx-favorites--user-favorite-list
+ (sx-cache-get 'question-favorites))
+ (sx-favorites-update)))
+;; Append to ensure `sx-network--initialize is run before it.
+(add-hook 'sx-init--internal-hook #'sx-favorites--initialize 'append)
(defun sx-favorites--retrieve-favorites (site)
"Obtain list of starred QUESTION_IDs for SITE."
@@ -65,18 +64,17 @@ in FAVORITE-LIST is the numerical QUESTION_ID.")
"Update list of starred QUESTION_IDs for SITE.
Writes list to cache QUESTION-FAVORITES."
- (sx-favorites--ensure-favorite-list site)
- (let ((favs (sx-favorites--retrieve-favorites site))
- (site-cell (assoc site
- sx-favorites--user-favorite-list)))
+ (let* ((favs (sx-favorites--retrieve-favorites site))
+ (site-cell (assoc site
+ sx-favorites--user-favorite-list))
+ (fav-cell (mapcar #'cdar favs)))
(if site-cell
- (setcdr site-cell (mapcar #'cdar favs))
- (push (cons site favs) sx-favorites--user-favorite-list))
+ (setcdr site-cell fav-cell)
+ (push (cons site fav-cell) sx-favorites--user-favorite-list))
(sx-cache-set 'question-favorites sx-favorites--user-favorite-list)))
(defun sx-favorites-update ()
"Update all sites retrieved from `sx-network--user-sites'."
- (sx-network--ensure-user)
(mapc #'sx-favorites--update-site-favorites
sx-network--user-sites))
diff --git a/sx-networks.el b/sx-networks.el
index 315daba..755d62c 100644
--- a/sx-networks.el
+++ b/sx-networks.el
@@ -56,28 +56,30 @@
"Retrieve cached information for network user.
If cache is not available, retrieve current data."
- (or (and (sx-cache-get 'network-user)
- (setq sx-network--user-sites
+ (or (and (setq sx-network--user-information (sx-cache-get 'network-user)
+ sx-network--user-sites
(sx-network--map-site-url-to-site-api)))
(sx-network--update)))
(defun sx-network--update ()
- "Update user information."
- (setq sx-network--user-information
- (sx-method-call "me/associated"
- '((types . (main_site meta_site)))
- sx-network--user-filter
- 'warn))
- (setq sx-network--user-sites (sx-network--map-site-url-to-site-api))
- (sx-cache-set 'network-user sx-network--user-information))
-
-(defun sx-network--ensure-user ()
- "Ensure user-cache is available.
-
-This should be called during initialization."
+ "Update user information.
+
+Sets cache and then uses `sx-network--get-associated' to update
+the variables."
+ (sx-cache-set 'network-user
+ (sx-method-call "me/associated"
+ '((types . (main_site meta_site)))
+ sx-network--user-filter
+ 'warn))
+ (sx-network--get-associated))
+
+(defun sx-network--initialize ()
+ "Ensure network-user cache is available.
+
+Added as hook to initialization."
;; Cache was not retrieved, retrieve it.
- (unless sx-network--user-information
- (sx-network--get-associated)))
+ (sx-network--get-associated))
+(add-hook 'sx-init--internal-hook #'sx-network--initialize)
(defun sx-network--map-site-url-to-site-api ()
"Convert `me/associations' to a set of `api_site_parameter's.
diff --git a/sx-question-list.el b/sx-question-list.el
index 0639f3c..7dd0d00 100644
--- a/sx-question-list.el
+++ b/sx-question-list.el
@@ -28,6 +28,7 @@
(require 'sx-site)
(require 'sx-question)
(require 'sx-question-mode)
+(require 'sx-favorites)
;;; Customization
@@ -86,6 +87,11 @@
""
:group 'sx-question-list-faces)
+(defface sx-question-list-favorite
+ '((t :inherit sx-question-list-score-upvoted))
+ ""
+ :group 'sx-question-list-faces)
+
;;; Mode Definition
(define-derived-mode sx-question-list-mode tabulated-list-mode "Question List"
@@ -232,32 +238,38 @@ Used in the questions list to indicate a question was updated \"4d ago\"."
(defun sx-question-list--print-info (data)
"Convert `json-read' DATA into tabulated-list format."
(sx-assoc-let data
- (list
- data
- (vector
- (list (int-to-string .score)
- 'face (if .upvoted 'sx-question-list-score-upvoted
- 'sx-question-list-score))
- (list (int-to-string .answer_count)
- 'face (if (sx-question--accepted-answer-id data)
- 'sx-question-list-answers-accepted
- 'sx-question-list-answers))
- (concat
- (propertize
- .title
- 'face (if (sx-question--read-p data)
- 'sx-question-list-read-question
- ;; Increment `sx-question-list--unread-count' for the mode-line.
- (cl-incf sx-question-list--unread-count)
- 'sx-question-list-unread-question))
- (propertize " " 'display "\n ")
- (propertize (concat (sx-time-since .last_activity_date)
- sx-question-list-ago-string)
- 'face 'sx-question-list-date)
- " "
- (propertize (mapconcat #'sx-question--tag-format .tags " ")
- 'face 'sx-question-list-tags)
- (propertize " " 'display "\n"))))))
+ (let ((favorite (if (member .question_id
+ (assoc .site
+ sx-favorites--user-favorite-list))
+ (if (char-displayable-p ?\x2b26) "\x2b26" "*") " ")))
+ (list
+ data
+ (vector
+ (list (int-to-string .score)
+ 'face (if .upvoted 'sx-question-list-score-upvoted
+ 'sx-question-list-score))
+ (list (int-to-string .answer_count)
+ 'face (if (sx-question--accepted-answer-id data)
+ 'sx-question-list-answers-accepted
+ 'sx-question-list-answers))
+ (concat
+ (propertize
+ .title
+ 'face (if (sx-question--read-p data)
+ 'sx-question-list-read-question
+ ;; Increment `sx-question-list--unread-count' for the mode-line.
+ (cl-incf sx-question-list--unread-count)
+ 'sx-question-list-unread-question))
+ (propertize " " 'display "\n ")
+ (propertize favorite 'face 'sx-question-list-favorite)
+ " "
+ (propertize (concat (sx-time-since .last_activity_date)
+ sx-question-list-ago-string)
+ 'face 'sx-question-list-date)
+ " "
+ (propertize (mapconcat #'sx-question--tag-format .tags " ")
+ 'face 'sx-question-list-tags)
+ (propertize " " 'display "\n")))))))
(defun sx-question-list-view-previous (n)
"Hide this question, move to previous one, display it."
diff --git a/sx-question-mode.el b/sx-question-mode.el
index fa58512..089ee12 100644
--- a/sx-question-mode.el
+++ b/sx-question-mode.el
@@ -443,7 +443,7 @@ If ID is nil, use ID2 instead."
(save-match-data
(goto-char (point-min))
(when (search-forward-regexp
- (format (rx line-start (0+ blank) "[%s]:" (1+ blank)
+ (format (rx line-start (0+ blank) "[%s]:" (0+ blank)
(group-n 1 (1+ (not blank))))
(or id id2))
nil t)