Start implementing EH stdlib

This commit is contained in:
2026-01-23 11:08:52 +01:00
parent 187ba48dcf
commit 6db315a244
9 changed files with 217 additions and 9 deletions

View File

@@ -0,0 +1,36 @@
(ns emptyhead.newlib.delegate
"Delegation: treat one message as though it were another, enabling behaviour sharing and polymorphism."
(:require [emptyhead.thought.crud :as thought]
[emptyhead.idea.crud :as idea]
[emptyhead.thought.define :as def]
[emptyhead.thought.eval :as eval]
[emptyhead.thought.extend :as extend]
[emptyhead.newlib.core]))
(defn remove-delegate
"Undelegate `del` from `msg`."
[msg del]
(let [remover (thought/register-thought! [:EH :CORE :NOP] :ext-stages [[:EH :MSG :REMOVE-DELEGATE msg del]])]
(eval/execute! remover)))
;; FIXME Delegate order is currently undefined! Give this a proper order.
(defn add-delegate
"Register `del` as a delegate for `msg`: implementations defined for `del` will now run trigger on `msg` as well.
For instance, if message =(:foo :bar)= is defined and we =(add-delegate :quux :bar)= then =(:foo :quux)= will alias to =(:foo :bar)=.
Note that this also works on the left hand side."
[msg del]
(remove-delegate msg del)
(let [delegator (thought/register-thought!
[:EH :IO :RETURN]
:data del
:transient false)
remover (thought/register-thought! [:EH :IDEA :FORGET] :data delegator)]
(extend/register-extension! delegator [:EH :MSG :DELEGATE msg])
(extend/register-extension! remover [:EH :MSG :REMOVE-DELEGATE msg del])))
(defn get-delegates
"Get possible delegates for `msg`."
[msg]
(let [stage [:EH :MSG :DELEGATE msg]]
(-> (thought/register-thought! [:EH :CORE :CONTAINER] :ext-stages [stage])
eval/execute! thought/pop-stack second)))