1 /*
2  *  Make.org Core API
3  *  Copyright (C) 2020 Make.org
4  *
5  * This program is free software: you can redistribute it and/or modify
6  *  it under the terms of the GNU Affero General Public License as
7  *  published by the Free Software Foundation, either version 3 of the
8  *  License, or (at your option) any later version.
9  *
10  *  This program is distributed in the hope that it will be useful,
11  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
12  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
13  *  GNU Affero General Public License for more details.
14  *
15  *  You should have received a copy of the GNU Affero General Public License
16  *  along with this program.  If not, see <https://www.gnu.org/licenses/>.
17  *
18  */
19 
20 package org.make.api.technical.graphql
21 
22 import caliban.{GraphQL, RootResolver}
23 import caliban.schema._
24 import caliban.wrappers.Wrappers.{printErrors, printSlowQueries}
25 import grizzled.slf4j.Logging
26 import org.make.api.proposal.ProposalServiceComponent
27 import org.make.api.technical.graphql.GraphQLProposalQuery.{GraphQLProposalQueries, ProposalSearchParams}
28 import org.make.api.technical.graphql.GraphQLRuntimeComponent.{EnvType, RuntimeType}
29 import org.make.api.technical.graphql.GraphQLUtils._
30 import org.make.core.RequestContext
31 import zio.clock.Clock
32 import zio.console.Console
33 import zio.duration.durationInt
34 import zio.{FiberRef, Has, Task, ZIO}
35 
36 trait GraphQLRuntime {
37   def graphQLService: GraphQL[RuntimeType]
38 }
39 
40 trait GraphQLRuntimeComponent {
41   def graphQLRuntime: GraphQLRuntime
42 }
43 
44 object GraphQLRuntimeComponent {
45   type EnvType = FiberRef[RequestContext]
46   type RuntimeType = Console with Clock with Has[EnvType]
47 }
48 
49 trait DefaultGraphQLRuntimeComponent
50     extends GraphQLRuntimeComponent
51     with GraphQLAuthorServiceComponent
52     with GraphQLIdeaServiceComponent
53     with GraphQLOrganisationServiceComponent
54     with GraphQLQuestionServiceComponent
55     with GraphQLTagServiceComponent {
56   self: ProposalServiceComponent =>
57 
58   override def graphQLRuntime: GraphQLRuntime = new DefaultGraphQLRuntime
59 
60   import GraphQLArgBuilders._
61 
62   class DefaultGraphQLRuntime extends GraphQLRuntime with Logging {
63 
64     override lazy val graphQLService: GraphQL[RuntimeType] = {
65       val queries = GraphQLProposalQueries(search = { parameters =>
66         ZIO.accessM[RuntimeType](_.get[EnvType].get).flatMap(searchProposals(_, parameters))
67       })
68 
69       val runtimeSchema: GenericSchema[RuntimeType] = new GenericSchema[RuntimeType] {}
70       import runtimeSchema._
71 
72       GraphQL.graphQL(RootResolver(AllQueries(queries))) @@ printErrors @@ printSlowQueries(500.millis) @@ debugPrint
73     }
74 
75     private def searchProposals(
76       requestContext: RequestContext,
77       params: ProposalSearchParams
78     ): Task[Seq[GraphQLProposal]] = {
79       Task.fromFuture(
80         implicit ec =>
81           proposalService
82             .searchForUser(requestContext.userId, params.toSearchQuery(requestContext), requestContext, None, None)
83             .map {
84               _.results.map { proposal =>
85                 GraphQLProposal.fromProposalResponse(proposal)(
86                   authorDataSource,
87                   questionDataSource,
88                   organisationDataSource,
89                   tagDataSource,
90                   ideaDataSource
91                 )
92               }
93             }
94       )
95     }
96   }
97 }
98 
99 final case class AllQueries(proposal: GraphQLProposalQueries)
Line Stmt Id Pos Tree Symbol Tests Code
58 39150 2033 - 2058 Apply org.make.api.technical.graphql.DefaultGraphQLRuntimeComponent.DefaultGraphQLRuntime.<init> new DefaultGraphQLRuntimeComponent.this.DefaultGraphQLRuntime()
79 44059 2787 - 3331 Apply zio.Task.fromFuture zio.Task.fromFuture[Seq[org.make.api.technical.graphql.GraphQLProposal]](((implicit ec: scala.concurrent.ExecutionContext) => DefaultGraphQLRuntimeComponent.this.proposalService.searchForUser(requestContext.userId, params.toSearchQuery(requestContext), requestContext, scala.None, scala.None).map[Seq[org.make.api.technical.graphql.GraphQLProposal]](((x$3: org.make.api.proposal.ProposalsResultSeededResponse) => x$3.results.map[org.make.api.technical.graphql.GraphQLProposal](((proposal: org.make.api.proposal.ProposalResponse) => GraphQLProposal.fromProposalResponse(proposal)(DefaultGraphQLRuntimeComponent.this.authorDataSource, DefaultGraphQLRuntimeComponent.this.questionDataSource, DefaultGraphQLRuntimeComponent.this.organisationDataSource, DefaultGraphQLRuntimeComponent.this.tagDataSource, DefaultGraphQLRuntimeComponent.this.ideaDataSource)))))(ec)))
83 31562 2837 - 3323 ApplyToImplicitArgs scala.concurrent.Future.map DefaultGraphQLRuntimeComponent.this.proposalService.searchForUser(requestContext.userId, params.toSearchQuery(requestContext), requestContext, scala.None, scala.None).map[Seq[org.make.api.technical.graphql.GraphQLProposal]](((x$3: org.make.api.proposal.ProposalsResultSeededResponse) => x$3.results.map[org.make.api.technical.graphql.GraphQLProposal](((proposal: org.make.api.proposal.ProposalResponse) => GraphQLProposal.fromProposalResponse(proposal)(DefaultGraphQLRuntimeComponent.this.authorDataSource, DefaultGraphQLRuntimeComponent.this.questionDataSource, DefaultGraphQLRuntimeComponent.this.organisationDataSource, DefaultGraphQLRuntimeComponent.this.tagDataSource, DefaultGraphQLRuntimeComponent.this.ideaDataSource)))))(ec)