github.com/99designs/gqlgen@v0.17.45/graphql/playground/apollo_sandbox_playground.go (about) 1 package playground 2 3 import ( 4 "encoding/json" 5 "fmt" 6 "html/template" 7 "net/http" 8 ) 9 10 // NOTE: New version available at https://embeddable-sandbox.cdn.apollographql.com/ --> 11 var apolloSandboxPage = template.Must(template.New("ApolloSandbox").Parse(`<!doctype html> 12 <html> 13 14 <head> 15 <meta charset="utf-8"> 16 <title>{{.title}}</title> 17 <meta name="viewport" content="width=device-width,initial-scale=1"> 18 <link rel="icon" href="https://embeddable-sandbox.cdn.apollographql.com/_latest/public/assets/favicon-dark.png"> 19 <style> 20 body { 21 margin: 0; 22 overflow: hidden; 23 } 24 </style> 25 </head> 26 27 <body> 28 <div style="width: 100vw; height: 100vh;" id='embedded-sandbox'></div> 29 <script rel="preload" as="script" crossorigin="anonymous" integrity="{{.mainSRI}}" type="text/javascript" src="https://embeddable-sandbox.cdn.apollographql.com/02e2da0fccbe0240ef03d2396d6c98559bab5b06/embeddable-sandbox.umd.production.min.js"></script> 30 <script> 31 {{- if .endpointIsAbsolute}} 32 const url = {{.endpoint}}; 33 {{- else}} 34 const url = location.protocol + '//' + location.host + {{.endpoint}}; 35 {{- end}} 36 const options = JSON.parse({{.options}}) 37 new window.EmbeddedSandbox({ 38 target: '#embedded-sandbox', 39 initialEndpoint: url, 40 persistExplorerState: true, 41 ...options, 42 }); 43 </script> 44 </body> 45 </html>`)) 46 47 // ApolloSandboxHandler responsible for setting up the apollo sandbox playground 48 func ApolloSandboxHandler(title, endpoint string, opts ...ApolloSandboxOption) http.HandlerFunc { 49 options := &apolloSandboxOptions{ 50 HideCookieToggle: true, 51 InitialState: apolloSandboxInitialState{ 52 IncludeCookies: true, 53 PollForSchemaUpdates: false, 54 }, 55 } 56 57 for _, opt := range opts { 58 opt(options) 59 } 60 61 optionsBytes, err := json.Marshal(options) 62 if err != nil { 63 panic(fmt.Errorf("failed to marshal apollo sandbox options: %w", err)) 64 } 65 66 return func(w http.ResponseWriter, r *http.Request) { 67 err := apolloSandboxPage.Execute(w, map[string]interface{}{ 68 "title": title, 69 "endpoint": endpoint, 70 "endpointIsAbsolute": endpointHasScheme(endpoint), 71 "mainSRI": "sha256-pYhw/8TGkZxk960PMMpDtjhw9YtKXUzGv6XQQaMJSh8=", 72 "options": string(optionsBytes), 73 }) 74 if err != nil { 75 panic(err) 76 } 77 } 78 } 79 80 // See https://www.apollographql.com/docs/graphos/explorer/sandbox/#options --> 81 type apolloSandboxOptions struct { 82 HideCookieToggle bool `json:"hideCookieToggle"` 83 EndpointIsEditable bool `json:"endpointIsEditable"` 84 InitialState apolloSandboxInitialState `json:"initialState,omitempty"` 85 } 86 87 type apolloSandboxInitialState struct { 88 IncludeCookies bool `json:"includeCookies"` 89 Document string `json:"document,omitempty"` 90 Variables map[string]any `json:"variables,omitempty"` 91 Headers map[string]any `json:"headers,omitempty"` 92 CollectionId string `json:"collectionId,omitempty"` 93 OperationId string `json:"operationId,omitempty"` 94 PollForSchemaUpdates bool `json:"pollForSchemaUpdates"` 95 SharedHeaders map[string]any `json:"sharedHeaders,omitempty"` 96 } 97 98 type ApolloSandboxOption func(options *apolloSandboxOptions) 99 100 // WithApolloSandboxHideCookieToggle By default, the embedded Sandbox does not show the Include cookies toggle in its connection settings. 101 // 102 // Set hideCookieToggle to false to enable users of your embedded Sandbox instance to toggle the Include cookies setting. 103 func WithApolloSandboxHideCookieToggle(hideCookieToggle bool) ApolloSandboxOption { 104 return func(options *apolloSandboxOptions) { 105 options.HideCookieToggle = hideCookieToggle 106 } 107 } 108 109 // WithApolloSandboxEndpointIsEditable By default, the embedded Sandbox has a URL input box that is editable by users. 110 // 111 // Set endpointIsEditable to false to prevent users of your embedded Sandbox instance from changing the endpoint URL. 112 func WithApolloSandboxEndpointIsEditable(endpointIsEditable bool) ApolloSandboxOption { 113 return func(options *apolloSandboxOptions) { 114 options.EndpointIsEditable = endpointIsEditable 115 } 116 } 117 118 // WithApolloSandboxInitialStateIncludeCookies Set this value to true if you want the Sandbox to pass { credentials: 'include' } for its requests by default. 119 // 120 // If you set hideCookieToggle to false, users can override this default setting with the Include cookies toggle. (By default, the embedded Sandbox does not show the Include cookies toggle in its connection settings.) 121 // 122 // If you also pass the handleRequest option, this option is ignored. 123 // 124 // Read more about the fetch API and credentials here https://developer.mozilla.org/en-US/docs/Web/API/fetch#credentials 125 func WithApolloSandboxInitialStateIncludeCookies(includeCookies bool) ApolloSandboxOption { 126 return func(options *apolloSandboxOptions) { 127 options.InitialState.IncludeCookies = includeCookies 128 } 129 } 130 131 // WithApolloSandboxInitialStateDocument Document operation to populate in the Sandbox's editor on load. 132 // 133 // If you omit this, the Sandbox initially loads an example query based on your schema. 134 func WithApolloSandboxInitialStateDocument(document string) ApolloSandboxOption { 135 return func(options *apolloSandboxOptions) { 136 options.InitialState.Document = document 137 } 138 } 139 140 // WithApolloSandboxInitialStateVariables Variables containing initial variable values to populate in the Sandbox on load. 141 // 142 // If provided, these variables should apply to the initial query you provide for document. 143 func WithApolloSandboxInitialStateVariables(variables map[string]any) ApolloSandboxOption { 144 return func(options *apolloSandboxOptions) { 145 options.InitialState.Variables = variables 146 } 147 } 148 149 // WithApolloSandboxInitialStateHeaders Headers containing initial variable values to populate in the Sandbox on load. 150 // 151 // If provided, these variables should apply to the initial query you provide for document. 152 func WithApolloSandboxInitialStateHeaders(headers map[string]any) ApolloSandboxOption { 153 return func(options *apolloSandboxOptions) { 154 options.InitialState.Headers = headers 155 } 156 } 157 158 // WithApolloSandboxInitialStateCollectionIdAndOperationId The ID of a collection, paired with an operation ID to populate in the Sandbox on load. 159 // 160 // You can find these values from a registered graph in Studio by clicking the ... menu next to an operation in the Explorer of that graph and selecting View operation details. 161 func WithApolloSandboxInitialStateCollectionIdAndOperationId(collectionId, operationId string) ApolloSandboxOption { 162 return func(options *apolloSandboxOptions) { 163 options.InitialState.CollectionId = collectionId 164 options.InitialState.OperationId = operationId 165 } 166 } 167 168 // WithApolloSandboxInitialStatePollForSchemaUpdates If true, the embedded Sandbox periodically polls your initialEndpoint for schema updates. 169 // 170 // The default value is false. 171 func WithApolloSandboxInitialStatePollForSchemaUpdates(pollForSchemaUpdates bool) ApolloSandboxOption { 172 return func(options *apolloSandboxOptions) { 173 options.InitialState.PollForSchemaUpdates = pollForSchemaUpdates 174 } 175 } 176 177 // WithApolloSandboxInitialStateSharedHeaders Headers that are applied by default to every operation executed by the embedded Sandbox. 178 // 179 // Users can disable the application of these headers, but they can't modify their values. 180 // 181 // The embedded Sandbox always includes these headers in its introspection queries to your initialEndpoint. 182 func WithApolloSandboxInitialStateSharedHeaders(sharedHeaders map[string]any) ApolloSandboxOption { 183 return func(options *apolloSandboxOptions) { 184 options.InitialState.SharedHeaders = sharedHeaders 185 } 186 }