Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Fix #4: Add code generator #15

Merged
merged 21 commits into from
Mar 15, 2018
Merged

Fix #4: Add code generator #15

merged 21 commits into from
Mar 15, 2018

Conversation

jonas
Copy link
Collaborator

@jonas jonas commented Jan 11, 2018

Ports the Scala code generator from sangria-codegen.

Refs #4

@jonas jonas requested a review from muuki88 January 11, 2018 12:15
@jonas
Copy link
Collaborator Author

jonas commented Jan 11, 2018

I didn't check the whether the naming of settings is consistent with the other plugins.

Also Scalameta now is at version 2.0 so an upgrade might be in order. I still think we can get rid of Scalameta if we use another mean of formatting code as it is generated.

@muuki88
Copy link
Owner

muuki88 commented Jan 11, 2018

Awesome :)

I would add my changes once cleaned up to this pull request.

I haven't used scala meta until now. Surely we could write our own
generator, but I don't have any detailed experience or opinion what
is more suitable / better maintainable in the long run.

object autoImport {
val graphqlCodegenSchema = taskKey[File]("GraphQL schema file")
val graphqlCodegenQueries = taskKey[Seq[File]]("GraphQL query documents")
val graphqlCodegenPackage =
Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I may change my settings to Codegen instead of CodeGen

}

result match {
case Left(error) => sys.error("Failed to generate code: $error")
Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Interpolation missing.

}
)

def parseIntrospectionSchemaFile(schemaFile: File): Result[Schema[_, _]] =
Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'll try to refactor these things into one helper. There's already the SchemaLoader which
I would enhance to match both, code and schema generation, use cases.

if (document == Builder.emptyDocumentResult)
copy(document = validatedQuery)
else
copy(document = document.flatMap(doc => validatedQuery.map(doc.merge)))
Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

That puzzled me in the beginning a lot 😄
With this we get the "single module" structure in the output, right?

If we would like to build one module per query, we wouldn't need this?

/**
* Generate code using Scalameta.
*/
case class ScalametaGenerator(moduleName: Term.Name,
Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We are not adding comments yet to the generated class. In the future we should do that
so users have a proper scaladoc ( if they use graphql comments).

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

True, let's create a ticket.

Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Done in #16


val StarWarsDir = file(sys.props("codegen.samples.dir")) / "starwars"

val server = project
Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

this example helped me a lot :) thanks

@muuki88
Copy link
Owner

muuki88 commented Jan 13, 2018

Sorry, I rebased instead of merging from master :(

@muuki88
Copy link
Owner

muuki88 commented Feb 11, 2018

Next round :) A couple of things

  • Upgraded to scalameta 2
  • Renamed a few things for clarity
  • Added GraphQLQuery trait generation
  • Added CodeGenStyle for an easier selection of code generation style

@jonas
Copy link
Collaborator Author

jonas commented Feb 17, 2018

This PR is getting big. I'll make a review today.

@muuki88
Copy link
Owner

muuki88 commented Feb 17, 2018

Indeed 😅
Digging more and more through your code and understanding things deeper. I'm actually close to getting this feature complete and then clean up even more things.

My deepest respect for figuring all this out ☺️

@muuki88
Copy link
Owner

muuki88 commented Feb 17, 2018

And I want to incorporate your code generator along with the new "Apollo Style" generator.

@@ -1 +1 @@
sbt.version=1.0.4
sbt.version=1.1.0
Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

1.1.1 was recently released

@@ -17,58 +17,67 @@ object GraphQLQueryPlugin extends AutoPlugin {
*/
val graphqlValidateQueries: TaskKey[Unit] =
taskKey[Unit]("validate all queries in the graphql source directory")

val graphqlQueryDirectory: SettingKey[File] =
settingKey[File]("graphql files")
Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The description seems off.

Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Good point. Will fix that

val schema = Schema.buildFromAst(schemaDocument)
// TODO separate these into two auto plugins
override def projectSettings: Seq[Setting[_]] =
pluginSettings(Compile) ++ pluginSettings(IntegrationTest)
Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

What is the goal of the it settings?

Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I wasn't sure at this point if the query validation is unit or integration test.
Then I decided to add them both, which is probably not the best idea. I'll remove the
integration test settings. I'll do that in #18

Nil
val schema = Schema.buildFromAst(schemaDocument)

log.info(s"Checking graphl files in ${graphqlQueryDirectory.value}")
Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

graphl => graphql

@@ -1 +1 @@
sbt.version=1.0.2
sbt.version=1.1.0
Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Maybe 1.1.1

}

result match {
case Left(error) => sys.error("Failed to generate code: $error")
case Left(error) => sys.error(s"Failed to generate code: $error")
Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

👍

scalaVersion := "2.12.4",
organization := "rocks.muki",
libraryDependencies ++= Seq(
"org.sangria-graphql" %% "sangria" % "1.3.2",
Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It might be useful to expose the sangria version used by the plugin for projects that want to keep them in sync?

@@ -17,5 +17,6 @@ TaskKey[Unit]("check") := {
""".stripMargin.trim

assert(file.exists)
assert(IO.read(file).trim == expected)
val generated = IO.read(file).trim
assert(generated == expected, s"Generated file:\n$generated")
Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

👍

build.sbt Outdated
@@ -9,7 +9,7 @@ libraryDependencies ++= Seq(
"io.circe" %% "circe-core" % circeVersion,
"io.circe" %% "circe-parser" % circeVersion,
"org.scalaj" %% "scalaj-http" % "2.3.0",
"org.scalameta" %% "scalameta" % "1.8.0",
"org.scalameta" %% "scalameta" % "2.1.2",
Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

There's now also 3.x version. But I think that can wait.

/**
* Generate code using Scalameta.
*/
case class ScalametaGenerator(moduleName: Term.Name,
Copy link
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

True, let's create a ticket.

@muuki88
Copy link
Owner

muuki88 commented Mar 15, 2018

@jonas what do you think? Should we merge this and continue improving this in smaller commits :)

@jonas
Copy link
Collaborator Author

jonas commented Mar 15, 2018 via email

@muuki88 muuki88 merged commit 9f55fb9 into master Mar 15, 2018
@jonas jonas deleted the codegen branch March 15, 2018 21:26
@jonas
Copy link
Collaborator Author

jonas commented Mar 15, 2018

🎉

@muuki88
Copy link
Owner

muuki88 commented Mar 15, 2018

Yeah 🤩🤩

I'll start documenting ASAP.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

None yet

2 participants