Skip to content

HTTPS clone URL

Subversion checkout URL

You can clone with HTTPS or Subversion.

Download ZIP

Loading…

Allow modifiying the repository-session #54

Closed
xeqi opened this Issue · 2 comments

3 participants

@xeqi

After exploring #50 and finding it didn't work 100%, I dove in to find out how the version collision merging works in Aether before it decides which jar to use. This mechanism provides a way to error on version ranges. However, it requires being able to change the DependencyGraphTransformer on the RepositorySystemSession.

I'm not sure the best way to provide access to do this. Some options I can think of:

  1. Pass in a function that gets called with the results of repository-session.
  2. Pass in a DependencyGraphTransformer that gets composed with the one already in the repository-session.
  3. Pass in a RepositorySystemSession
  4. Pass in a function that makes a RepositorySystemSession, and takes arguments like repository-session.

As a motivating example, using option 1, I can define

(defn- check-for-range [node parents]
  (prn node)
  (prn (.getDependency node))
  (if-let [d (.getDependency node)]
    (prn (.getFile (.getArtifact d))))
  (if-let [vc (.getVersionConstraint node)]
    (if-not (empty? (.getRanges vc))
      (throw (ex-info (str (->> (conj parents node)
                                (map #(if-let [dependency (.getDependency %)]
                                        (if-let [artifact (.getArtifact dependency)]
                                          (str "["
                                               (.getGroupId artifact)
                                               "/"
                                               (.getArtifactId artifact)
                                               " \""
                                               (.getVersionConstraint %)
                                               "\"]"))))
                                (remove nil?)
                                (interpose " -> ")
                                (apply str))
                           " version range bad!!")
                      {}))))
  (every? #(check-for-range % (conj parents node))
          (.getChildren node)))

(defn add-no-ranges-transformer [session]
  (.setDependencyGraphTransformer
       session
       (ChainedDependencyGraphTransformer.
        (into-array DependencyGraphTransformer
                    [(reify DependencyGraphTransformer
                       (transformGraph [self node context]
                         (check-for-range node [])
                         node))
                     (.getDependencyGraphTransformer session)]))))

This allows me to get output like:

tester.core> (ae/resolve-dependencies
              :coordinates '[[net.cgrand/regex "1.1.0"] [org.clojure/clojure "1.4.0"]]
              :repositories (merge ae/maven-central {"clojars" "https://clojars.org/repo"})
              :modify-session add-no-ranges-transformer)
ExceptionInfo [net.cgrand/regex "1.1.0"] -> [org.clojure/clojure "[1.2.0,)"] version range bad!!  clojure.core/ex-info (core.clj:4227)

tester.core> (ae/resolve-dependencies
              :coordinates '[[net.cgrand/regex "1.1.0"]]
              :repositories (merge ae/maven-central {"clojars" "https://clojars.org/repo"})
              :modify-session add-no-ranges-transformer)
ExceptionInfo [net.cgrand/regex "1.1.0"] -> [org.clojure/clojure "[1.2.0,)"] version range bad!!  clojure.core/ex-info (core.clj:4227)

tester.core> (ae/resolve-dependencies
              :coordinates '[[org.clojure/clojure "[1.4.0]"]]
              :repositories (merge ae/maven-central {"clojars" "https://clojars.org/repo"})
              :modify-session add-no-ranges-transformer)
ExceptionInfo [org.clojure/clojure "[1.4.0,1.4.0]"] version range bad!!  clojure.core/ex-info (core.clj:4227)
@cemerick
Owner

My first impulse is to have repository-session change to take an option map, make it public, and let people hook the var if they need to do anything crazy. ;-) The API for resolve-dependencies et al. is already so complicated that I hesitate to pile in any of the other options mentioned. Will ponder.

@hugoduncan

making repository-session public, and allowing it as a keyword argument on resolve-dependencies et al. seems simplest to me.

@cemerick cemerick closed this issue from a commit
@xeqi xeqi Provide opportunity to change RespositorySystemSession
Make respository-session public so it can be wrapped.

Allow passing in :repository-session-fn to be used
for creating a repository-session.

Fixes #54.
4070a44
@cemerick cemerick closed this in 4070a44
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Something went wrong with that request. Please try again.