msolli / proletarian

A durable job queuing and worker system for Clojure backed by PostgreSQL.
MIT License
161 stars 7 forks source link

Job handlers would ideally use a Component/Integrant component/system as an argument #21

Closed vemv closed 8 months ago

vemv commented 8 months ago

Hi!

Thanks for the excellent lib.

I've noticed it's common for job handlers to require the Component/Integrant system to do anything useful.

(If not the entire system, it could be at least a specific component or selection of components).

e.g. a job handler will commonly need the database.

While I could save the Integrant system to a global var, that's not intended usage. It would also easily result in circular references.

I believe that a reasonable pattern/solution would be:

This is how it would look like for consumers:

(defmethod integrant.core/init-key ::worker [_ {::keys [db mailer redis]}]
  (proletarian.worker/create-queue-worker db
                                          handle-job!
                                          {:proletarian/payload-middleware (fn [payload]
                                                                             (assoc payload
                                                                                    ::db db
                                                                                    ::mailer mailer
                                                                                    ::redis redis))})
  ,,,)

(that's not technically middleware - other names welcome)

WDYT?

Thanks - V

msolli commented 8 months ago

Hi, thanks for reaching out!

Whenever I have a handle-job! function that needs more information (or state) than the Proletarian worker provides, I capture it from the scope where create-queue-worker is called:

(defn handle-job! [{::keys [db mailer redis]} job-type payload]
  ;; handle the job...
)

(defmethod integrant.core/init-key ::worker [_ {::keys [db mailer redis]}]
  (proletarian.worker/create-queue-worker db
                                          (partial handle-job! {::db db
                                                                ::mailer mailer
                                                                ::redis redis})
                                          {#_the-options-map})
  ,,,)

Would this work for you?

vemv commented 8 months ago

That seems to make sense!

I'll give it a try - update during the week hopefully.

vemv commented 8 months ago

This worked nicely.

Thanks for the suggestion!