Browse code
feat: intern refs
Edward Langley authored on 22/10/2023 09:17:53
Showing 6 changed files
Showing 6 changed files
... | ... |
@@ -1,8 +1,7 @@ |
1 | 1 |
(in-package :fwoar.cl-git) |
2 | 2 |
|
3 |
-(defclass git-commit () |
|
4 |
- ((%hash :initarg :hash :reader hash) |
|
5 |
- (%metadata :initarg :metadata :reader metadata) |
|
3 |
+(defclass git-commit (git-object) |
|
4 |
+ ((%metadata :initarg :metadata :reader metadata) |
|
6 | 5 |
(%data :initarg :data :reader data))) |
7 | 6 |
|
8 | 7 |
(defmethod print-object ((o git-commit) s) |
... | ... |
@@ -35,9 +34,6 @@ |
35 | 34 |
hash)) |
36 | 35 |
|
37 | 36 |
|
38 |
-(defmethod component ((component (eql :hash)) (object git-commit)) |
|
39 |
- (hash object)) |
|
40 |
- |
|
41 | 37 |
(defmethod component ((component (eql :tree)) (object git-commit)) |
42 | 38 |
(ensure-ref |
43 | 39 |
(cadr |
... | ... |
@@ -14,7 +14,7 @@ |
14 | 14 |
()) |
15 | 15 |
|
16 | 16 |
(defclass git-object () |
17 |
- ()) |
|
17 |
+ ((%hash :initarg :hash :accessor hash))) |
|
18 | 18 |
|
19 | 19 |
(defgeneric object-type->sym (object-type) |
20 | 20 |
(:documentation "Canonicalizes different representations of an |
... | ... |
@@ -146,3 +146,6 @@ |
146 | 146 |
(serapeum:string-replace (namestring (user-homedir-pathname)) |
147 | 147 |
(root-of (ref-repo obj)) |
148 | 148 |
"~/")))) |
149 |
+ |
|
150 |
+(defmethod component ((component (eql :hash)) (object git-object)) |
|
151 |
+ (hash object)) |
... | ... |
@@ -1,9 +1,15 @@ |
1 | 1 |
(in-package :fwoar.cl-git) |
2 | 2 |
|
3 |
-(defclass+ blob () |
|
3 |
+(defclass+ blob (git-object) |
|
4 | 4 |
((%data :reader data :initarg :data))) |
5 | 5 |
|
6 |
-(defgeneric -extract-object-of-type (type s repository &key &allow-other-keys) |
|
6 |
+(defgeneric -extract-object-of-type (type s repository &key &allow-other-keys) |
|
7 |
+ (:method :around (type s repository &key hash) |
|
8 |
+ (let ((result (call-next-method))) |
|
9 |
+ (prog1 result |
|
10 |
+ (when (typep result 'git-object) |
|
11 |
+ (setf (hash result) hash))))) |
|
12 |
+ |
|
7 | 13 |
(:method ((type (eql :blob)) s repository &key) |
8 | 14 |
(blob s)) |
9 | 15 |
|
... | ... |
@@ -27,10 +27,16 @@ |
27 | 27 |
:file object-file)) |
28 | 28 |
(packed-ref repo id)))) |
29 | 29 |
|
30 |
+(defvar *ref-intern-table* |
|
31 |
+ (make-hash-table :test 'equal #+sbcl :weakness #+sbcl :key-and-value)) |
|
32 |
+ |
|
30 | 33 |
(defun ensure-ref (thing &optional (repo *git-repository*)) |
31 | 34 |
(typecase thing |
32 | 35 |
(git-ref thing) |
33 |
- (t (ref repo thing)))) |
|
36 |
+ (t (alexandria:when-let ((maybe-result (ref repo thing))) |
|
37 |
+ (alexandria:ensure-gethash (component :hash maybe-result) |
|
38 |
+ *ref-intern-table* |
|
39 |
+ maybe-result))))) |
|
34 | 40 |
|
35 | 41 |
(defun ensure-repository (thing) |
36 | 42 |
(repository thing)) |
... | ... |
@@ -6,11 +6,10 @@ |
6 | 6 |
(defun git-tree (entries) |
7 | 7 |
(fw.lu:new 'git-tree entries)) |
8 | 8 |
|
9 |
-(defclass tree-entry () |
|
9 |
+(defclass tree-entry (git-object) |
|
10 | 10 |
((%repo :initarg :repo :reader repository) |
11 | 11 |
(%mode :initarg :mode :reader te-mode) |
12 |
- (%name :initarg :name :reader te-name) |
|
13 |
- (%hash :initarg :hash :reader te-hash))) |
|
12 |
+ (%name :initarg :name :reader te-name))) |
|
14 | 13 |
|
15 | 14 |
(defun tree-entry (repo name mode hash) |
16 | 15 |
(fw.lu:new 'tree-entry repo name mode hash)) |
... | ... |
@@ -65,8 +64,6 @@ |
65 | 64 |
(te-name object)) |
66 | 65 |
(defmethod component ((component (eql :mode)) (object tree-entry)) |
67 | 66 |
(te-mode object)) |
68 |
-(defmethod component ((component (eql :hash)) (object tree-entry)) |
|
69 |
- (te-hash object)) |
|
70 | 67 |
(defmethod component ((component (eql :ref)) (object tree-entry)) |
71 | 68 |
(ref (repository object) |
72 | 69 |
(te-hash object))) |