graphql-docs 0.6.2 → 1.0.0.pre

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (31) hide show
  1. checksums.yaml +4 -4
  2. data/README.md +14 -37
  3. data/Rakefile +15 -3
  4. data/graphql-docs.gemspec +0 -1
  5. data/lib/graphql-docs.rb +24 -10
  6. data/lib/graphql-docs/configuration.rb +5 -7
  7. data/lib/graphql-docs/generator.rb +31 -34
  8. data/lib/graphql-docs/helpers.rb +12 -63
  9. data/lib/graphql-docs/layouts/assets/_sass/_content.scss +22 -0
  10. data/lib/graphql-docs/layouts/assets/_sass/_deprecations.scss +9 -0
  11. data/lib/graphql-docs/layouts/assets/css/screen.scss +1 -0
  12. data/lib/graphql-docs/layouts/graphql_enums.html +4 -4
  13. data/lib/graphql-docs/layouts/graphql_input_objects.html +5 -5
  14. data/lib/graphql-docs/layouts/graphql_interfaces.html +17 -5
  15. data/lib/graphql-docs/layouts/graphql_mutations.html +14 -6
  16. data/lib/graphql-docs/layouts/graphql_objects.html +12 -12
  17. data/lib/graphql-docs/layouts/graphql_operation.html +19 -0
  18. data/lib/graphql-docs/layouts/graphql_scalars.html +2 -2
  19. data/lib/graphql-docs/layouts/graphql_unions.html +4 -4
  20. data/lib/graphql-docs/layouts/includes/arguments.html +3 -6
  21. data/lib/graphql-docs/layouts/includes/connections.html +4 -4
  22. data/lib/graphql-docs/layouts/includes/fields.html +16 -20
  23. data/lib/graphql-docs/layouts/includes/input_fields.html +5 -9
  24. data/lib/graphql-docs/layouts/includes/possible_types.html +1 -1
  25. data/lib/graphql-docs/layouts/includes/sidebar.html +10 -26
  26. data/lib/graphql-docs/layouts/includes/values.html +9 -2
  27. data/lib/graphql-docs/parser.rb +174 -29
  28. data/lib/graphql-docs/version.rb +1 -1
  29. metadata +6 -20
  30. data/lib/graphql-docs/client.rb +0 -55
  31. data/lib/graphql-docs/layouts/assets/_sass/screen.scss +0 -647
@@ -2,10 +2,17 @@
2
2
 
3
3
  <% values.each do |value| %>
4
4
 
5
- <h4 class="name"><%= value['name'] %></h4>
5
+ <h4 class="name"><%= value[:name] %></h4>
6
6
 
7
7
  <div class="description-wrapper">
8
- <%= value['description'] %>
8
+ <% if value[:is_deprecated] %>
9
+ <div class="deprecation-notice <%= classes[:deprecation_notice] %>">
10
+ <span class="deprecation-title">Deprecation notice</span>
11
+ <%= markdown.(value[:deprecation_reason]) %>
12
+ </div>
13
+ <% end %>
14
+
15
+ <p><%= value[:description] %></p>
9
16
  </div>
10
17
 
11
18
  <% end %>
@@ -1,51 +1,196 @@
1
+ require 'graphql'
2
+
1
3
  module GraphQLDocs
2
4
  class Parser
3
- attr_reader :schema, :processed_schema
5
+ include Helpers
6
+
7
+ attr_reader :processed_schema
4
8
 
5
- def initialize(response, options)
9
+ def initialize(schema, options)
6
10
  @options = options
7
- @schema = JSON.parse(response)['data']
8
- @processed_schema = @schema.dup['__schema']
11
+ @schema = GraphQL::Schema.from_definition(schema)
12
+ @processed_schema = {
13
+ operation_types: [],
14
+ mutation_types: [],
15
+ object_types: [],
16
+ interface_types: [],
17
+ enum_types: [],
18
+ union_types: [],
19
+ input_object_types: [],
20
+ scalar_types: [],
21
+ }
9
22
  end
10
23
 
11
24
  def parse
12
- # sort the types
13
- @processed_schema['types'] = @processed_schema['types'].sort_by { |key, _| key['name'] }
25
+ @schema.types.values.each do |object|
26
+ data = {}
14
27
 
15
- # fetch the connections
16
- @processed_schema['types'].each do |object|
17
- next if object['fields'].nil?
18
- object['connections'] = object['fields'].select { |f| next if f.is_a?(Array); connection?(f) }
19
- end
28
+ case object
29
+ when ::GraphQL::ObjectType
30
+ if object.name == 'Query'
31
+ data[:name] = object.name
32
+ data[:description] = object.description
20
33
 
21
- # fetch the kinds of items
22
- type_kinds = @processed_schema['types'].map { |h| h['kind'] }.uniq
23
- type_kinds.each do |kind|
24
- @processed_schema["#{kind.downcase}_types"] = @processed_schema['types'].select { |t| t['kind'] == kind }
25
- end
26
- mutation_types = @processed_schema['object_types'].select do |t|
27
- t['name'] == 'Mutation'
34
+ data[:interfaces] = object.interfaces.map(&:name).sort
35
+ data[:fields], data[:connections] = fetch_fields(object.fields)
36
+
37
+ @processed_schema[:operation_types] << data
38
+ elsif object.name == 'Mutation'
39
+ data[:name] = object.name
40
+ data[:description] = object.description
41
+
42
+ @processed_schema[:operation_types] << data
43
+
44
+ object.fields.values.each do |mutation|
45
+ h = {}
46
+ h[:name] = mutation.name
47
+ h[:description] = mutation.description
48
+ h[:input_fields], _ = fetch_fields(mutation.arguments.values.first.type.unwrap.input_fields)
49
+ h[:return_fields], _ = fetch_fields(mutation.type.unwrap.fields)
50
+
51
+ @processed_schema[:mutation_types] << h
52
+ end
53
+ else
54
+ data[:name] = object.name
55
+ data[:description] = object.description
56
+
57
+ data[:interfaces] = object.interfaces.map(&:name).sort
58
+ data[:fields], data[:connections] = fetch_fields(object.fields)
59
+
60
+ @processed_schema[:object_types] << data
61
+ end
62
+ when ::GraphQL::InterfaceType
63
+ data[:name] = object.name
64
+ data[:description] = object.description
65
+ data[:fields], data[:connections] = fetch_fields(object.fields)
66
+
67
+ @processed_schema[:interface_types] << data
68
+ when ::GraphQL::EnumType
69
+ data[:name] = object.name
70
+ data[:description] = object.description
71
+
72
+ data[:values] = object.values.values.map do |val|
73
+ h = {}
74
+ h[:name] = val.name
75
+ h[:description] = val.description
76
+ unless val.deprecation_reason.nil?
77
+ h[:is_deprecated] = true
78
+ h[:deprecation_reason] = val.deprecation_reason
79
+ end
80
+ h
81
+ end
82
+
83
+ @processed_schema[:enum_types] << data
84
+ when ::GraphQL::UnionType
85
+ data[:name] = object.name
86
+ data[:description] = object.description
87
+ data[:possible_types] = object.possible_types.map(&:name).sort
88
+
89
+ @processed_schema[:union_types] << data
90
+ when ::GraphQL::InputObjectType
91
+ data[:name] = object.name
92
+ data[:description] = object.description
93
+
94
+ data[:input_fields], _ = fetch_fields(object.input_fields)
95
+
96
+ @processed_schema[:input_object_types] << data
97
+ when ::GraphQL::ScalarType
98
+ data[:name] = object.name
99
+ data[:description] = object.description
100
+
101
+ @processed_schema[:scalar_types] << data
102
+ else
103
+ raise TypeError, "I'm not sure what #{object.class} is!"
104
+ end
28
105
  end
29
106
 
30
- @processed_schema['mutation_types'] = if mutation_types.empty?
31
- []
32
- else
33
- @processed_schema['mutation_types'] = mutation_types.first['fields']
34
- end
107
+ @processed_schema[:mutation_types].sort_by! { |o| o[:name] }
108
+ @processed_schema[:object_types].sort_by! { |o| o[:name] }
109
+ @processed_schema[:interface_types].sort_by! { |o| o[:name] }
110
+ @processed_schema[:enum_types].sort_by! { |o| o[:name] }
111
+ @processed_schema[:union_types].sort_by! { |o| o[:name] }
112
+ @processed_schema[:input_object_types].sort_by! { |o| o[:name] }
113
+ @processed_schema[:scalar_types].sort_by! { |o| o[:name] }
35
114
 
36
- # TODO: should the 'types' key be deleted now?
115
+ @processed_schema[:interface_types].each do |interface|
116
+ interface[:implemented_by] = []
117
+ @processed_schema[:object_types].each do |obj|
118
+ if obj[:interfaces].include?(interface[:name])
119
+ interface[:implemented_by] << obj[:name]
120
+ end
121
+ end
122
+ end
37
123
 
38
124
  @processed_schema
39
125
  end
40
126
 
41
127
  private
42
128
 
43
- def connection?(hash)
44
- if hash['type']['ofType'] && hash['type']['ofType']['name'] && hash['type']['ofType']['name'].end_with?('Connection')
45
- true
46
- else
47
- false
129
+ def fetch_fields(object_fields)
130
+ fields = connections = []
131
+
132
+ object_fields.values.each do |field|
133
+ hash = {}
134
+
135
+ hash[:name] = field.name
136
+ hash[:description] = field.description
137
+ if field.respond_to?(:deprecation_reason) && !field.deprecation_reason.nil?
138
+ hash[:is_deprecated] = true
139
+ hash[:deprecation_reason] = field.deprecation_reason
140
+ end
141
+
142
+ hash[:type] = generate_type(field.type)
143
+
144
+ if field.respond_to?(:arguments)
145
+ hash[:arguments] = []
146
+ field.arguments.values.each do |arg|
147
+ h = {}
148
+ h[:name] = arg.name
149
+ h[:description] = arg.description
150
+ h[:type] = generate_type(arg.type)
151
+
152
+ hash[:arguments] << h
153
+ end
154
+ end
155
+
156
+ if field.type.unwrap.name.end_with?('Connection')
157
+ connections << hash
158
+ else
159
+ fields << hash
160
+ end
48
161
  end
162
+
163
+ [fields, connections]
164
+ end
165
+
166
+ def generate_type(type)
167
+ name = type.unwrap.to_s
168
+ path = case type.unwrap
169
+ when ::GraphQL::ObjectType
170
+ if name == 'Query'
171
+ 'operation'
172
+ else
173
+ 'object'
174
+ end
175
+ when ::GraphQL::ScalarType
176
+ 'scalar'
177
+ when ::GraphQL::InterfaceType
178
+ 'interface'
179
+ when ::GraphQL::EnumType
180
+ 'enum'
181
+ when ::GraphQL::InputObjectType
182
+ 'input_object'
183
+ when ::GraphQL::UnionType
184
+ 'union'
185
+ else
186
+ raise TypeError, "Unknown type: `#{type.unwrap.class}`"
187
+ end
188
+
189
+ {
190
+ name: name,
191
+ path: path + '/' + slugify(name),
192
+ info: type.to_s
193
+ }
49
194
  end
50
195
  end
51
196
  end
@@ -1,3 +1,3 @@
1
1
  module GraphQLDocs
2
- VERSION = '0.6.2'
2
+ VERSION = '1.0.0.pre'
3
3
  end
metadata CHANGED
@@ -1,29 +1,15 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: graphql-docs
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.6.2
4
+ version: 1.0.0.pre
5
5
  platform: ruby
6
6
  authors:
7
7
  - Garen Torikian
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2017-06-07 00:00:00.000000000 Z
11
+ date: 2017-09-12 00:00:00.000000000 Z
12
12
  dependencies:
13
- - !ruby/object:Gem::Dependency
14
- name: faraday
15
- requirement: !ruby/object:Gem::Requirement
16
- requirements:
17
- - - "<"
18
- - !ruby/object:Gem::Version
19
- version: '0.10'
20
- type: :runtime
21
- prerelease: false
22
- version_requirements: !ruby/object:Gem::Requirement
23
- requirements:
24
- - - "<"
25
- - !ruby/object:Gem::Version
26
- version: '0.10'
27
13
  - !ruby/object:Gem::Dependency
28
14
  name: graphql
29
15
  requirement: !ruby/object:Gem::Requirement
@@ -250,7 +236,6 @@ files:
250
236
  - Rakefile
251
237
  - graphql-docs.gemspec
252
238
  - lib/graphql-docs.rb
253
- - lib/graphql-docs/client.rb
254
239
  - lib/graphql-docs/configuration.rb
255
240
  - lib/graphql-docs/generator.rb
256
241
  - lib/graphql-docs/helpers.rb
@@ -265,6 +250,7 @@ files:
265
250
  - lib/graphql-docs/landing_pages/union.md
266
251
  - lib/graphql-docs/layouts/assets/_sass/_api-box.scss
267
252
  - lib/graphql-docs/layouts/assets/_sass/_content.scss
253
+ - lib/graphql-docs/layouts/assets/_sass/_deprecations.scss
268
254
  - lib/graphql-docs/layouts/assets/_sass/_fonts.scss
269
255
  - lib/graphql-docs/layouts/assets/_sass/_header.scss
270
256
  - lib/graphql-docs/layouts/assets/_sass/_mobile.scss
@@ -273,7 +259,6 @@ files:
273
259
  - lib/graphql-docs/layouts/assets/_sass/_sidebar.scss
274
260
  - lib/graphql-docs/layouts/assets/_sass/_syntax.scss
275
261
  - lib/graphql-docs/layouts/assets/_sass/_types.scss
276
- - lib/graphql-docs/layouts/assets/_sass/screen.scss
277
262
  - lib/graphql-docs/layouts/assets/css/screen.scss
278
263
  - lib/graphql-docs/layouts/assets/images/graphiql-headers.png
279
264
  - lib/graphql-docs/layouts/assets/images/graphiql-variables.png
@@ -302,6 +287,7 @@ files:
302
287
  - lib/graphql-docs/layouts/graphql_interfaces.html
303
288
  - lib/graphql-docs/layouts/graphql_mutations.html
304
289
  - lib/graphql-docs/layouts/graphql_objects.html
290
+ - lib/graphql-docs/layouts/graphql_operation.html
305
291
  - lib/graphql-docs/layouts/graphql_scalars.html
306
292
  - lib/graphql-docs/layouts/graphql_unions.html
307
293
  - lib/graphql-docs/layouts/includes/arguments.html
@@ -331,9 +317,9 @@ required_ruby_version: !ruby/object:Gem::Requirement
331
317
  version: '0'
332
318
  required_rubygems_version: !ruby/object:Gem::Requirement
333
319
  requirements:
334
- - - ">="
320
+ - - ">"
335
321
  - !ruby/object:Gem::Version
336
- version: '0'
322
+ version: 1.3.1
337
323
  requirements: []
338
324
  rubyforge_project:
339
325
  rubygems_version: 2.6.12
@@ -1,55 +0,0 @@
1
- require 'faraday'
2
- require 'graphql'
3
-
4
- module GraphQLDocs
5
- class Client
6
- attr_accessor :faraday
7
-
8
- def initialize(options)
9
- @login = options[:login]
10
- @password = options[:password]
11
-
12
- if @login.nil? && !@password.nil?
13
- fail ArgumentError, 'Client provided a login, but no password!'
14
- end
15
-
16
- if !@login.nil? && @password.nil?
17
- fail ArgumentError, 'Client provided a password, but no login!'
18
- end
19
-
20
- @access_token = options[:access_token]
21
-
22
- @url = options[:url]
23
- @headers = options[:headers]
24
- @faraday = Faraday.new(url: @url, headers: @headers)
25
-
26
- if @login && @password
27
- @faraday.basic_auth(@login, @password)
28
- elsif @access_token
29
- @faraday.authorization('token', @access_token)
30
- end
31
- end
32
-
33
- def fetch
34
- res = @faraday.post do |req|
35
- req.headers['Content-Type'] = 'application/json'
36
- req.body = "{ \"query\": \"#{GraphQL::Introspection::INTROSPECTION_QUERY.gsub("\n", '')}\" }"
37
- end
38
- res.body
39
- end
40
-
41
- def inspect
42
- inspected = super
43
-
44
- # mask password
45
- inspected = inspected.gsub! @password, '*******' if @password
46
-
47
- # Only show last 4 of token, secret
48
- if @access_token
49
- inspected = inspected.gsub! @access_token, "#{'*'*36}#{@access_token[36..-1]}"
50
- end
51
-
52
- inspected
53
- end
54
- end
55
- end
@@ -1,647 +0,0 @@
1
- @charset "utf-8";
2
- @import 'normalize';
3
- @import 'variables';
4
- @import 'icon-font';
5
- @import 'pygments';
6
-
7
- /*
8
- Copyright 2008-2013 Concur Technologies, Inc.
9
-
10
- Licensed under the Apache License, Version 2.0 (the "License"); you may
11
- not use this file except in compliance with the License. You may obtain
12
- a copy of the License at
13
-
14
- http://www.apache.org/licenses/LICENSE-2.0
15
-
16
- Unless required by applicable law or agreed to in writing, software
17
- distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
18
- WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
19
- License for the specific language governing permissions and limitations
20
- under the License.
21
- */
22
-
23
- ////////////////////////////////////////////////////////////////////////////////
24
- // GENERAL STUFF
25
- ////////////////////////////////////////////////////////////////////////////////
26
-
27
- html, body {
28
- color: $main-text;
29
- padding: 0;
30
- margin: 0;
31
- -webkit-font-smoothing: antialiased;
32
- -moz-osx-font-smoothing: grayscale;
33
- @extend %default-font;
34
- background-color: $main-bg;
35
- height: 100%;
36
- -webkit-text-size-adjust: none; /* Never autoresize text */
37
- }
38
-
39
- ////////////////////////////////////////////////////////////////////////////////
40
- // TABLE OF CONTENTS
41
- ////////////////////////////////////////////////////////////////////////////////
42
-
43
- #toc > ul > li > a > span {
44
- float: right;
45
- background-color: #2484FF;
46
- border-radius: 40px;
47
- width: 20px;
48
- }
49
-
50
- @mixin embossed-bg {
51
- background:
52
- linear-gradient(to bottom, rgba(#000, 0.2), rgba(#000, 0) 8px),
53
- linear-gradient(to top, rgba(#000, 0.2), rgba(#000, 0) 8px),
54
- linear-gradient(to bottom, rgba($nav-embossed-border-top, 1), rgba($nav-embossed-border-top, 0) 1.5px),
55
- linear-gradient(to top, rgba($nav-embossed-border-bottom, 1), rgba($nav-embossed-border-bottom, 0) 1.5px),
56
- $nav-subitem-bg;
57
- }
58
-
59
- .tocify-wrapper {
60
- transition: left 0.3s ease-in-out;
61
-
62
- overflow-y: auto;
63
- overflow-x: hidden;
64
- position: fixed;
65
- z-index: 30;
66
- top: 0;
67
- left: 0;
68
- bottom: 0;
69
- width: $nav-width;
70
- background-color: $nav-bg;
71
- font-size: 13px;
72
- font-weight: bold;
73
-
74
- // language selector for mobile devices
75
- .lang-selector {
76
- display: none;
77
- a {
78
- padding-top: 0.5em;
79
- padding-bottom: 0.5em;
80
- }
81
- }
82
-
83
- // This is the logo at the top of the ToC
84
- &>img {
85
- display: block;
86
- max-width: 100%;
87
- }
88
-
89
- &>.search {
90
- position: relative;
91
-
92
- input {
93
- background: $nav-bg;
94
- border-width: 0 0 1px 0;
95
- border-color: $search-box-border-color;
96
- padding: 6px 0 6px 20px;
97
- box-sizing: border-box;
98
- margin: $nav-v-padding $nav-padding;
99
- width: $nav-width - 30;
100
- outline: none;
101
- color: $nav-text;
102
- border-radius: 0; /* ios has a default border radius */
103
- }
104
-
105
- &:before {
106
- position: absolute;
107
- top: 17px;
108
- left: $nav-padding;
109
- color: $nav-text;
110
- @extend %icon-search;
111
- }
112
- }
113
-
114
- img+.tocify {
115
- margin-top: $logo-margin;
116
- }
117
-
118
- .search-results {
119
- margin-top: 0;
120
- box-sizing: border-box;
121
- height: 0;
122
- overflow-y: auto;
123
- overflow-x: hidden;
124
- transition-property: height, margin;
125
- transition-duration: 180ms;
126
- transition-timing-function: ease-in-out;
127
- &.visible {
128
- height: 30%;
129
- margin-bottom: 1em;
130
- }
131
-
132
- @include embossed-bg;
133
-
134
- li {
135
- margin: 1em $nav-padding;
136
- line-height: 1;
137
- }
138
-
139
- a {
140
- color: $nav-text;
141
- text-decoration: none;
142
-
143
- &:hover {
144
- text-decoration: underline;
145
- }
146
- }
147
- }
148
-
149
- .tocify-item>a, .toc-footer li {
150
- padding: 0 $nav-padding 0 $nav-padding;
151
- display: block;
152
- overflow-x: hidden;
153
- white-space: nowrap;
154
- text-overflow: ellipsis;
155
- }
156
-
157
- // The Table of Contents is composed of multiple nested
158
- // unordered lists. These styles remove the default
159
- // styling of an unordered list because it is ugly.
160
- ul, li {
161
- list-style: none;
162
- margin: 0;
163
- padding: 0;
164
- line-height: 28px;
165
- }
166
-
167
- li {
168
- color: $nav-text;
169
- transition-property: background;
170
- transition-timing-function: linear;
171
- transition-duration: 230ms;
172
-
173
- a {
174
- color: $nav-text;
175
- text-decoration: none;
176
- }
177
- }
178
-
179
- // This is the currently selected ToC entry
180
- .tocify-focus {
181
- box-shadow: 0px 1px 0px $nav-active-shadow;
182
- background-color: $nav-active-bg;
183
- color: $nav-active-text;
184
- }
185
-
186
- // Subheaders are the submenus that slide open
187
- // in the table of contents.
188
- .tocify-subheader {
189
- display: none; // tocify will override this when needed
190
- background-color: $nav-subitem-bg;
191
- font-weight: 500;
192
- .tocify-item>a {
193
- padding-left: $nav-padding + $nav-indent;
194
- font-size: 12px;
195
- }
196
-
197
- // for embossed look:
198
- @include embossed-bg;
199
- &>li:last-child {
200
- box-shadow: none; // otherwise it'll overflow out of the subheader
201
- }
202
- }
203
-
204
- .toc-footer {
205
- padding: 1em 0;
206
- margin-top: 1em;
207
- border-top: 1px dashed $nav-footer-border-color;
208
-
209
- li,a {
210
- color: $nav-text;
211
- text-decoration: none;
212
- }
213
-
214
- a:hover {
215
- text-decoration: underline;
216
- }
217
-
218
- li {
219
- font-size: 0.8em;
220
- line-height: 1.7;
221
- text-decoration: none;
222
- }
223
- }
224
-
225
- }
226
-
227
- // button to show navigation on mobile devices
228
- #nav-button {
229
- span {
230
- display: block;
231
- $side-pad: $main-padding / 2 - 8px;
232
- padding: $side-pad $side-pad $side-pad;
233
- background-color: rgba($main-bg, 0.7);
234
- transform-origin: 0 0;
235
- transform: rotate(-90deg) translate(-100%, 0);
236
- border-radius: 0 0 0 5px;
237
- }
238
- padding: 0 1.5em 5em 0; // increase touch size area
239
- display: none;
240
- position: fixed;
241
- top: 0;
242
- left: 0;
243
- z-index: 100;
244
- color: #000;
245
- text-decoration: none;
246
- font-weight: bold;
247
- opacity: 0.7;
248
- line-height: 16px;
249
- img {
250
- height: 16px;
251
- vertical-align: bottom;
252
- }
253
-
254
- transition: left 0.3s ease-in-out;
255
-
256
- &:hover { opacity: 1; }
257
- &.open {left: $nav-width}
258
- }
259
-
260
-
261
- ////////////////////////////////////////////////////////////////////////////////
262
- // PAGE LAYOUT AND CODE SAMPLE BACKGROUND
263
- ////////////////////////////////////////////////////////////////////////////////
264
-
265
- .page-wrapper {
266
- margin-left: $nav-width;
267
- position: relative;
268
- z-index: 10;
269
- background-color: $main-bg;
270
- min-height: 100%;
271
-
272
- padding-bottom: 1px; // prevent margin overflow
273
-
274
- // The dark box is what gives the code samples their dark background.
275
- // It sits essentially under the actual content block, which has a
276
- // transparent background.
277
- // I know, it's hackish, but it's the simplist way to make the left
278
- // half of the content always this background color.
279
- .dark-box {
280
- // width: $examples-width;
281
- background-color: $examples-bg;
282
- position: absolute;
283
- right: 0;
284
- top: 0;
285
- bottom: 0;
286
- }
287
-
288
- .lang-selector {
289
- position: fixed;
290
- z-index: 50;
291
- border-bottom: 5px solid $lang-select-active-bg;
292
- }
293
- }
294
-
295
- .lang-selector {
296
- background-color: $lang-select-bg;
297
- width: 100%;
298
- font-weight: bold;
299
- a {
300
- display: block;
301
- float:left;
302
- color: $lang-select-text;
303
- text-decoration: none;
304
- padding: 0 10px;
305
- line-height: 30px;
306
- outline: 0;
307
-
308
- &:active, &:focus {
309
- background-color: $lang-select-pressed-bg;
310
- color: $lang-select-pressed-text;
311
- }
312
-
313
- &.active {
314
- background-color: $lang-select-active-bg;
315
- color: $lang-select-active-text;
316
- }
317
- }
318
-
319
- &:after {
320
- content: '';
321
- clear: both;
322
- display: block;
323
- }
324
- }
325
-
326
- ////////////////////////////////////////////////////////////////////////////////
327
- // CONTENT STYLES
328
- ////////////////////////////////////////////////////////////////////////////////
329
- // This is all the stuff with the light background in the left half of the page
330
-
331
- .content {
332
- // to place content above the dark box
333
- position: relative;
334
- z-index: 30;
335
-
336
- &:after {
337
- content: '';
338
- display: block;
339
- clear: both;
340
- }
341
-
342
- &>h1, &>h2, &>h3, &>h4, &>h5, &>h6, &>p, &>table, &>ul, &>ol, &>aside, &>dl {
343
- // margin-right: $examples-width;
344
- padding: 0 $main-padding;
345
- box-sizing: border-box;
346
- display: block;
347
- text-shadow: $main-embossed-text-shadow;
348
-
349
- @extend %left-col;
350
- }
351
-
352
- &>ul, &>ol {
353
- padding-left: $main-padding + 15px;
354
- }
355
-
356
- // the div is the tocify hidden div for placeholding stuff
357
- &>h1, &>h2, &>div:not(.highlighter-rouge) {
358
- clear:both;
359
- }
360
-
361
- h1 {
362
- @extend %header-font;
363
- font-size: 30px;
364
- padding-top: 0.5em;
365
- padding-bottom: 0.5em;
366
- border-bottom: 1px solid #ccc;
367
- margin-bottom: $h1-margin-bottom;
368
- margin-top: 2em;
369
- border-top: 1px solid #ddd;
370
- background-image: linear-gradient(to bottom, #fff, #f9f9f9);
371
- }
372
-
373
- h1:first-child, div:first-child + h1 {
374
- border-top-width: 0;
375
- margin-top: 0;
376
- }
377
-
378
- h2 {
379
- @extend %header-font;
380
- font-size: 20px;
381
- margin-top: 4em;
382
- margin-bottom: 0;
383
- border-top: 1px solid #ccc;
384
- padding-top: 1.2em;
385
- padding-bottom: 1.2em;
386
- background-image: linear-gradient(to bottom, rgba(#fff, 0.4), rgba(#fff, 0));
387
- }
388
-
389
- // h2s right after h1s should bump right up
390
- // against the h1s.
391
- h1 + h2, h1 + div + h2 {
392
- margin-top: $h1-margin-bottom * -1;
393
- border-top: none;
394
- }
395
-
396
- h3, h4, h5, h6 {
397
- @extend %header-font;
398
- font-size: 15px;
399
- margin-top: 2.5em;
400
- margin-bottom: 0.8em;
401
- }
402
-
403
- h4, h5, h6 {
404
- font-size: 10px;
405
- }
406
-
407
- hr {
408
- margin: 2em 0;
409
- border-top: 2px solid $examples-bg;
410
- border-bottom: 2px solid $main-bg;
411
- }
412
-
413
- table {
414
- margin-bottom: 1em;
415
- overflow: auto;
416
- th,td {
417
- text-align: left;
418
- vertical-align: top;
419
- line-height: 1.6;
420
- }
421
-
422
- th {
423
- padding: 5px 10px;
424
- border-bottom: 1px solid #ccc;
425
- vertical-align: bottom;
426
- }
427
-
428
- td {
429
- padding: 10px;
430
- }
431
-
432
- tr:last-child {
433
- border-bottom: 1px solid #ccc;
434
- }
435
-
436
- tr:nth-child(odd)>td {
437
- background-color: lighten($main-bg,4.2%);
438
- }
439
-
440
- tr:nth-child(even)>td {
441
- background-color: lighten($main-bg,2.4%);
442
- }
443
- }
444
-
445
- dt {
446
- font-weight: bold;
447
- }
448
-
449
- dd {
450
- margin-left: 15px;
451
- }
452
-
453
- p, li, dt, dd {
454
- line-height: 1.6;
455
- margin-top: 0;
456
- }
457
-
458
- img {
459
- max-width: 100%;
460
- }
461
-
462
- code {
463
- background-color: rgba(0,0,0,0.05);
464
- padding: 3px;
465
- border-radius: 3px;
466
- @extend %break-words;
467
- @extend %code-font;
468
- }
469
-
470
- pre>code {
471
- background-color: transparent;
472
- padding: 0;
473
- }
474
-
475
- aside {
476
- padding-top: 1em;
477
- padding-bottom: 1em;
478
- text-shadow: 0 1px 0 lighten($aside-notice-bg, 15%);
479
- margin-top: 1.5em;
480
- margin-bottom: 1.5em;
481
- background: $aside-notice-bg;
482
- line-height: 1.6;
483
-
484
- &.warning {
485
- background-color: $aside-warning-bg;
486
- text-shadow: 0 1px 0 lighten($aside-warning-bg, 15%);
487
- }
488
-
489
- &.success {
490
- background-color: $aside-success-bg;
491
- text-shadow: 0 1px 0 lighten($aside-success-bg, 15%);
492
- }
493
- }
494
-
495
- aside:before {
496
- vertical-align: middle;
497
- padding-right: 0.5em;
498
- font-size: 14px;
499
- }
500
-
501
- aside.notice:before {
502
- @extend %icon-info-sign;
503
- }
504
-
505
- aside.warning:before {
506
- @extend %icon-exclamation-sign;
507
- }
508
-
509
- aside.success:before {
510
- @extend %icon-ok-sign;
511
- }
512
-
513
- .search-highlight {
514
- padding: 2px;
515
- margin: -2px;
516
- border-radius: 4px;
517
- border: 1px solid #F7E633;
518
- text-shadow: 1px 1px 0 #666;
519
- background: linear-gradient(to top left, #F7E633 0%, #F1D32F 100%);
520
- }
521
- }
522
-
523
- .content {
524
- .field-entry {
525
- padding: 0 $main-padding;
526
-
527
- .description-wrapper {
528
- display: none;
529
- }
530
- &.expanded {
531
- .description-wrapper {
532
- display: block;
533
- }
534
- }
535
- }
536
- }
537
-
538
- ////////////////////////////////////////////////////////////////////////////////
539
- // CODE SAMPLE STYLES
540
- ////////////////////////////////////////////////////////////////////////////////
541
- // This is all the stuff that appears in the right half of the page
542
-
543
- .content {
544
- pre, blockquote {
545
- background-color: $code-bg;
546
- color: #fff;
547
-
548
- padding: 2em $main-padding;
549
- margin: 0;
550
- width: $examples-width;
551
-
552
- float:right;
553
- clear:right;
554
-
555
- box-sizing: border-box;
556
- text-shadow: 0px 1px 2px rgba(0,0,0,0.4);
557
-
558
- @extend %right-col;
559
-
560
- &>p { margin: 0; }
561
-
562
- a {
563
- color: #fff;
564
- text-decoration: none;
565
- border-bottom: dashed 1px #ccc;
566
- }
567
- }
568
-
569
- pre {
570
- @extend %code-font;
571
- }
572
-
573
- blockquote {
574
- &>p {
575
- background-color: $code-annotation-bg;
576
- border-radius: 5px;
577
- padding: $code-annotation-padding;
578
- color: #ccc;
579
- border-top: 1px solid #000;
580
- border-bottom: 1px solid #404040;
581
- }
582
- }
583
- }
584
-
585
- ////////////////////////////////////////////////////////////////////////////////
586
- // RESPONSIVE DESIGN
587
- ////////////////////////////////////////////////////////////////////////////////
588
- // These are the styles for phones and tablets
589
- // There are also a couple styles disperesed
590
-
591
- @media (max-width: $tablet-width) {
592
- .tocify-wrapper {
593
- left: -$nav-width;
594
-
595
- &.open {
596
- left: 0;
597
- }
598
- }
599
-
600
- .page-wrapper {
601
- margin-left: 0;
602
- }
603
-
604
- #nav-button {
605
- display: block;
606
- }
607
-
608
- .tocify-wrapper .tocify-item > a {
609
- padding-top: 0.3em;
610
- padding-bottom: 0.3em;
611
- }
612
- }
613
-
614
- @media (max-width: $phone-width) {
615
- .dark-box {
616
- display: none;
617
- }
618
-
619
- %left-col {
620
- margin-right: 0;
621
- }
622
-
623
- .tocify-wrapper .lang-selector {
624
- display: block;
625
- }
626
-
627
- .page-wrapper .lang-selector {
628
- display: none;
629
- }
630
-
631
- %right-col {
632
- width: auto;
633
- float: none;
634
- }
635
-
636
- %right-col + %left-col {
637
- margin-top: $main-padding;
638
- }
639
- }
640
-
641
- .highlight .c, .highlight .cm, .highlight .c1, .highlight .cs {
642
- color: #909090;
643
- }
644
-
645
- .highlight, .highlight .w {
646
- background-color: $code-bg;
647
- }