47degrees/github4s

Changing API URL

Closed this issue · 8 comments

Is there a way of changing the API URLs? I would like to use this library against an Enterprise GitHub and so I need to change the default URL.

I found that it is implicitly passed to individual constructors of the APIs in Interpreters.scala, but I have no idea if it can be changed to something else.

Just as a side note, I really like the design of the library in principle, but it is very hard to use for people that don't have experience with Cats. You should consider either improving the docs (I couldn't even get the current Getting Started to compile) or providing a higher level API on top, that does not leak the Monad abstractions and underlying libraries.

It would indeed be interesting to have a way to specify different urls.

However, I'm curious as to which part of the getting started didn't compile?

Here is an example:

package some-package

import cats._
import cats.Eval._
import github4s.{Github, HttpRequestBuilder, HttpRequestBuilderExtension, HttpRequestBuilderExtensionJVM}
import github4s.Github._
import github4s.GithubResponses.GHResponse
import github4s.free.interpreters.Capture
import github4s.jvm.Implicits._

import scalaj.http._
import org.scalatest.{FunSpec, Matchers}

class GitHubPublisherSpec extends FunSpec with Matchers {
  describe("GitHub API") {
    it("should find keys") {

      val aa = Github(None).gitData.getReference("org-name", "repo-name", "tags").exec[Eval, HttpResponse[String]]().value
      println(aa)
    }
  }
}

I was getting errors about implicit divergence until I added these two imports:

import cats._
import cats.Eval._

I'm sure it's easy to figure out when you know Cats, but it took me about an hour, only to later find out that I can't use the library at all because of the custom URLs.

Weird, I followed the example using only:

scala> import github4s.Github
import github4s.Github

scala> import github4s.jvm.Implicits._
import github4s.jvm.Implicits._

scala> import cats.Eval
import cats.Eval

scala> import github4s.Github._
import github4s.Github._

scala> import scalaj.http._
import scalaj.http._

scala> val user1 = Github(Some("TOKEN")).users.get("rafaparadela")
user1: github4s.GithubResponses.GHIO[github4s.GithubResponses.GHResponse[github4s.free.domain.User]] = Free(...)

scala> val u1 = user1.exec[Eval, HttpResponse[String]]().value
u1: github4s.GithubResponses.GHResponse[github4s.free.domain.User] = Right(GHResult(User(315070,rafaparadela,https://avatars0.githubusercontent.com/u/315070?v=3,https://github.com/rafaparadela,Some(Rafa Paradela),Some(rafa.p@47deg.com),Some(47 Degrees),Some(http://rafaparadela.github.io),Some(Cádiz, Spain),Some(Hola)),200,Map(etag -> Vector(W/"4d6a7b32d456d87a30be600e752e9862"), server -> Vector(GitHub.com), x-served-by -> Vector(15bc4ab707db6d6b474783868c7cc828), x-xss-protection -> Vector(1; mode=block), access-control-allow-origin -> Vector(*), cache-control -> Vector(private, max-age=60, s-maxage=60), content-security-policy -> Vector(default-src 'none'), x-ratelimit-remaining -> Vector(4975), access-control-expose-headers -> Vector(ETag, Link, X-GitHub-OTP...

without any issues

I should probably mention that this was inside a SBT plugin, so on 2.10 and the exact problem was that the FlatMap implicit from cats was missing and so the evalMonadError could not be completed.

Anyways I'm sorry if I came off as overly critical, your response has been phenomenal and as I mentioned already earlier I really like the design of the library, I just need to get better at Category theory.

Yeah no problem, we're just working on documentation at the moment so any feedback is appreciated 👍

Hi @mirosval , just in case you're interested, we've been using github4s from an sbt plugin.

You can see more over it here: https://github.com/47deg/sbt-org-policies/blob/24017395ab523f1d9a4bbbd2e20a72cfb9f76d8d/core/src/main/scala/sbtorgpolicies/github/GitHubOps.scala

svshb commented

There are somewhat ugly but working hack to change urls:

val clazz = GithubDefaultUrls.getClass
val field = clazz.getDeclaredField("defaultUrls")
val accessibility = field.isAccessible
field.setAccessible(true)
field.set(
  GithubDefaultUrls,
  GithubApiUrls(
    "https://api.github.com/",
    "https://github.com/login/oauth/authorize?client_id=%s&redirect_uri=%s&scope=%s&state=%s",
    "https://github.com/login/oauth/access_token"
  )
)
field.setAccessible(accessibility)

It still would be nice to have a proper way to set url's :)

bilki commented

I think there is no easy way to change this without breaking current users programs, as there is an explicit import of GithubDefaultUrls in the Interpreters file.

Removing this import breaks the compilation, and adding a new implicit that fixes that in the Interpreters class argument list forces a change upwards into Implicits files to allow the user to inject its own GithubApiUrls (or import github4s.GithubDefaultUrls._)