better_errors 2.9.0 → 2.10.0

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.
@@ -2,706 +2,14 @@
2
2
  <html>
3
3
  <head>
4
4
  <title><%= exception_type %> at <%= request_path %></title>
5
+ <link rel="icon" href="data:;base64,=" />
5
6
  </head>
6
- <body>
7
+ <body class="better-errors-javascript-not-loaded">
7
8
  <%# Stylesheets are placed in the <body> for Turbolinks compatibility. %>
8
- <style>
9
- /* Basic reset */
10
- * {
11
- margin: 0;
12
- padding: 0;
13
- }
14
-
15
- table {
16
- width: 100%;
17
- border-collapse: collapse;
18
- }
19
-
20
- th, td {
21
- vertical-align: top;
22
- text-align: left;
23
- }
24
-
25
- textarea {
26
- resize: none;
27
- }
28
-
29
- body {
30
- font-size: 10pt;
31
- }
32
-
33
- body, td, input, textarea {
34
- font-family: helvetica neue, lucida grande, sans-serif;
35
- line-height: 1.5;
36
- color: #333;
37
- text-shadow: 0 1px 0 rgba(255, 255, 255, 0.6);
38
- }
39
-
40
- html {
41
- background: #f0f0f5;
42
- }
43
-
44
- .clearfix::after{
45
- clear: both;
46
- content: ".";
47
- display: block;
48
- height: 0;
49
- visibility: hidden;
50
- }
51
-
52
- /* ---------------------------------------------------------------------
53
- * Basic layout
54
- * --------------------------------------------------------------------- */
55
-
56
- /* Small */
57
- @media screen and (max-width: 1100px) {
58
- html {
59
- overflow-y: scroll;
60
- }
61
-
62
- body {
63
- margin: 0 20px;
64
- }
65
-
66
- header.exception {
67
- margin: 0 -20px;
68
- }
69
-
70
- nav.sidebar {
71
- padding: 0;
72
- margin: 20px 0;
73
- }
74
-
75
- ul.frames {
76
- max-height: 200px;
77
- overflow: auto;
78
- }
79
- }
80
-
81
- /* Wide */
82
- @media screen and (min-width: 1100px) {
83
- header.exception {
84
- position: fixed;
85
- top: 0;
86
- left: 0;
87
- right: 0;
88
- }
89
-
90
- nav.sidebar,
91
- .frame_info {
92
- position: fixed;
93
- top: 102px;
94
- bottom: 0;
95
-
96
- box-sizing: border-box;
97
-
98
- overflow-y: auto;
99
- overflow-x: hidden;
100
- }
101
-
102
- nav.sidebar {
103
- width: 40%;
104
- left: 20px;
105
- top: 122px;
106
- bottom: 20px;
107
- }
108
-
109
- .frame_info {
110
- right: 0;
111
- left: 40%;
112
-
113
- padding: 20px;
114
- padding-left: 10px;
115
- margin-left: 30px;
116
- }
117
- }
118
-
119
- nav.sidebar {
120
- background: #d3d3da;
121
- border-top: solid 3px #a33;
122
- border-bottom: solid 3px #a33;
123
- border-radius: 4px;
124
- box-shadow: 0 0 6px rgba(0, 0, 0, 0.2), inset 0 0 0 1px rgba(0, 0, 0, 0.1);
125
- }
126
-
127
- /* ---------------------------------------------------------------------
128
- * Header
129
- * --------------------------------------------------------------------- */
130
-
131
- header.exception {
132
- padding: 18px 20px;
133
-
134
- height: 66px;
135
- min-height: 59px;
136
-
137
- overflow: hidden;
138
-
139
- background-color: #20202a;
140
- color: #aaa;
141
- text-shadow: 0 1px 0 rgba(0, 0, 0, 0.3);
142
- font-weight: 200;
143
- box-shadow: inset 0 -5px 3px -3px rgba(0, 0, 0, 0.05), inset 0 -1px 0 rgba(0, 0, 0, 0.05);
144
-
145
- -webkit-text-smoothing: antialiased;
146
- }
147
-
148
- /* Heading */
149
- header.exception .fix-actions {
150
- margin-top: .5em;
151
- }
152
-
153
- header.exception .fix-actions input[type=submit] {
154
- font-weight: bold;
155
- }
156
-
157
- header.exception h2 {
158
- font-weight: 200;
159
- font-size: 11pt;
160
- }
161
-
162
- header.exception h2,
163
- header.exception p {
164
- line-height: 1.5em;
165
- overflow: hidden;
166
- white-space: pre;
167
- text-overflow: ellipsis;
168
- }
169
-
170
- header.exception h2 strong {
171
- font-weight: 700;
172
- color: #d55;
173
- }
174
-
175
- header.exception p {
176
- font-weight: 200;
177
- font-size: 17pt;
178
- color: white;
179
- }
180
-
181
- header.exception:hover {
182
- height: auto;
183
- z-index: 2;
184
- }
185
-
186
- header.exception:hover h2,
187
- header.exception:hover p {
188
- padding-right: 20px;
189
- overflow-y: auto;
190
- word-wrap: break-word;
191
- white-space: pre-wrap;
192
- height: auto;
193
- max-height: 7.5em;
194
- }
195
-
196
- @media screen and (max-width: 1100px) {
197
- header.exception {
198
- height: auto;
199
- }
200
-
201
- header.exception h2,
202
- header.exception p {
203
- padding-right: 20px;
204
- overflow-y: auto;
205
- word-wrap: break-word;
206
- height: auto;
207
- max-height: 7em;
208
- }
209
- }
210
-
211
- <%#
212
- /* Light theme */
213
- header.exception {
214
- text-shadow: 0 1px 0 rgba(250, 250, 250, 0.6);
215
- background: rgba(200,100,50,0.10);
216
- color: #977;
217
- }
218
- header.exception h2 strong {
219
- color: #533;
220
- }
221
- header.exception p {
222
- color: #744;
223
- }
224
- %>
225
-
226
- /* ---------------------------------------------------------------------
227
- * Navigation
228
- * --------------------------------------------------------------------- */
229
-
230
- nav.tabs {
231
- border-bottom: solid 1px #ddd;
232
-
233
- background-color: #eee;
234
- text-align: center;
235
-
236
- padding: 6px;
237
-
238
- box-shadow: inset 0 1px 0 rgba(255, 255, 255, 0.1);
239
- }
240
-
241
- nav.tabs a {
242
- display: inline-block;
243
-
244
- height: 22px;
245
- line-height: 22px;
246
- padding: 0 10px;
247
-
248
- text-decoration: none;
249
- font-size: 8pt;
250
- font-weight: bold;
251
-
252
- color: #999;
253
- text-shadow: 0 1px 0 rgba(255, 255, 255, 0.6);
254
- }
255
-
256
- nav.tabs a.selected {
257
- color: white;
258
- background: rgba(0, 0, 0, 0.5);
259
- border-radius: 16px;
260
- box-shadow: 1px 1px 0 rgba(255, 255, 255, 0.1);
261
- text-shadow: 0 0 4px rgba(0, 0, 0, 0.4), 0 1px 0 rgba(0, 0, 0, 0.4);
262
- }
263
-
264
- nav.tabs a.disabled {
265
- text-decoration: line-through;
266
- text-shadow: none;
267
- cursor: default;
268
- }
269
-
270
- /* ---------------------------------------------------------------------
271
- * Sidebar
272
- * --------------------------------------------------------------------- */
273
-
274
- ul.frames {
275
- box-shadow: 0 0 10px rgba(0, 0, 0, 0.1);
276
- }
277
-
278
- /* Each item */
279
- ul.frames li {
280
- background-color: #f8f8f8;
281
- background: -webkit-linear-gradient(top, #f8f8f8 80%, #f0f0f0);
282
- background: -moz-linear-gradient(top, #f8f8f8 80%, #f0f0f0);
283
- background: linear-gradient(top, #f8f8f8 80%, #f0f0f0);
284
- box-shadow: inset 0 -1px 0 #e2e2e2;
285
- padding: 7px 20px;
286
-
287
- cursor: pointer;
288
- overflow: hidden;
289
- }
290
-
291
- ul.frames .name,
292
- ul.frames .location {
293
- overflow: hidden;
294
- height: 1.5em;
295
-
296
- white-space: nowrap;
297
- word-wrap: none;
298
- text-overflow: ellipsis;
299
- }
300
-
301
- ul.frames .method {
302
- color: #966;
303
- }
304
-
305
- ul.frames .location {
306
- font-size: 0.85em;
307
- font-weight: 400;
308
- color: #999;
309
- }
310
-
311
- ul.frames .line {
312
- font-weight: bold;
313
- }
314
-
315
- /* Selected frame */
316
- ul.frames li.selected {
317
- background: #38a;
318
- box-shadow: inset 0 1px 0 rgba(0, 0, 0, 0.1), inset 0 2px 0 rgba(255, 255, 255, 0.01), inset 0 -1px 0 rgba(0, 0, 0, 0.1);
319
- }
320
-
321
- ul.frames li.selected .name,
322
- ul.frames li.selected .method,
323
- ul.frames li.selected .location {
324
- color: white;
325
- text-shadow: 0 1px 0 rgba(0, 0, 0, 0.2);
326
- }
327
-
328
- ul.frames li.selected .location {
329
- opacity: 0.6;
330
- }
331
-
332
- /* Iconography */
333
- ul.frames li {
334
- padding-left: 60px;
335
- position: relative;
336
- }
337
-
338
- ul.frames li .icon {
339
- display: block;
340
- width: 20px;
341
- height: 20px;
342
- line-height: 20px;
343
- border-radius: 15px;
344
-
345
- text-align: center;
346
-
347
- background: white;
348
- border: solid 2px #ccc;
349
-
350
- font-size: 9pt;
351
- font-weight: 200;
352
- font-style: normal;
353
-
354
- position: absolute;
355
- top: 14px;
356
- left: 20px;
357
- }
358
-
359
- ul.frames .icon.application {
360
- background: #808090;
361
- border-color: #555;
362
- }
363
-
364
- ul.frames .icon.application:before {
365
- content: 'A';
366
- color: white;
367
- text-shadow: 0 0 3px rgba(0, 0, 0, 0.2);
368
- }
369
-
370
- /* Responsiveness -- flow to single-line mode */
371
- @media screen and (max-width: 1100px) {
372
- ul.frames li {
373
- padding-top: 6px;
374
- padding-bottom: 6px;
375
- padding-left: 36px;
376
- line-height: 1.3;
377
- }
378
-
379
- ul.frames li .icon {
380
- width: 11px;
381
- height: 11px;
382
- line-height: 11px;
383
-
384
- top: 7px;
385
- left: 10px;
386
- font-size: 5pt;
387
- }
388
-
389
- ul.frames .name,
390
- ul.frames .location {
391
- display: inline-block;
392
- line-height: 1.3;
393
- height: 1.3em;
394
- }
395
-
396
- ul.frames .name {
397
- margin-right: 10px;
398
- }
399
- }
400
-
401
- /* ---------------------------------------------------------------------
402
- * Monospace
403
- * --------------------------------------------------------------------- */
404
-
405
- pre, code, .be-repl input, .be-repl .command-line span, textarea, .code_linenums {
406
- font-family: menlo, lucida console, monospace;
407
- font-size: 8pt;
408
- }
409
-
410
- /* ---------------------------------------------------------------------
411
- * Display area
412
- * --------------------------------------------------------------------- */
413
-
414
- .trace_info {
415
- background: #fff;
416
- padding: 6px;
417
- border-radius: 3px;
418
- margin-bottom: 2px;
419
- box-shadow: 0 0 10px rgba(0, 0, 0, 0.03), 1px 1px 0 rgba(0, 0, 0, 0.05), -1px 1px 0 rgba(0, 0, 0, 0.05), 0 0 0 4px rgba(0, 0, 0, 0.04);
420
- }
421
-
422
- .code_block{
423
- background: #f1f1f1;
424
- border-left: 1px solid #ccc;
425
- }
426
-
427
- /* Titlebar */
428
- .trace_info .title {
429
- background: #f1f1f1;
430
-
431
- box-shadow: inset 0 1px 0 rgba(255, 255, 255, 0.3);
432
- overflow: hidden;
433
- padding: 6px 10px;
434
-
435
- border: solid 1px #ccc;
436
- border-bottom: 0;
437
-
438
- border-top-left-radius: 2px;
439
- border-top-right-radius: 2px;
440
- }
441
-
442
- .trace_info .title .name,
443
- .trace_info .title .location {
444
- font-size: 9pt;
445
- line-height: 26px;
446
- height: 26px;
447
- overflow: hidden;
448
- }
449
-
450
- .trace_info .title .location {
451
- float: left;
452
- font-weight: bold;
453
- font-size: 10pt;
454
- }
455
-
456
- .trace_info .title .location a {
457
- color:inherit;
458
- text-decoration:none;
459
- border-bottom:1px solid #aaaaaa;
460
- }
461
-
462
- .trace_info .title .location a:hover {
463
- border-color:#666666;
464
- }
465
-
466
- .trace_info .title .name {
467
- float: right;
468
- font-weight: 200;
469
- }
470
-
471
- .code, .be-console, .unavailable {
472
- background: #fff;
473
- padding: 5px;
474
-
475
- box-shadow: inset 3px 3px 3px rgba(0, 0, 0, 0.1), inset 0 0 0 1px rgba(0, 0, 0, 0.1);
476
- }
477
-
478
- .code_linenums{
479
- background:#f1f1f1;
480
- padding-top:10px;
481
- padding-bottom:9px;
482
- float:left;
483
- }
484
-
485
- .code_linenums span{
486
- display:block;
487
- padding:0 12px;
488
- }
489
-
490
- .code {
491
- margin-bottom: -1px;
492
- border-top-left-radius:2px;
493
- padding: 10px 0;
494
- overflow: auto;
495
- }
496
-
497
- .code pre{
498
- padding-left:12px;
499
- min-height:16px;
500
- }
501
-
502
- /* Source unavailable */
503
- p.unavailable {
504
- padding: 20px 0 40px 0;
505
- text-align: center;
506
- color: #b99;
507
- font-weight: bold;
508
- }
509
-
510
- p.unavailable:before {
511
- content: '\00d7';
512
- display: block;
513
-
514
- color: #daa;
515
-
516
- text-align: center;
517
- font-size: 40pt;
518
- font-weight: normal;
519
- margin-bottom: -10px;
520
- }
521
-
522
- @-webkit-keyframes highlight {
523
- 0% { background: rgba(220, 30, 30, 0.3); }
524
- 100% { background: rgba(220, 30, 30, 0.1); }
525
- }
526
- @-moz-keyframes highlight {
527
- 0% { background: rgba(220, 30, 30, 0.3); }
528
- 100% { background: rgba(220, 30, 30, 0.1); }
529
- }
530
- @keyframes highlight {
531
- 0% { background: rgba(220, 30, 30, 0.3); }
532
- 100% { background: rgba(220, 30, 30, 0.1); }
533
- }
534
-
535
- .code .highlight, .code_linenums .highlight {
536
- background: rgba(220, 30, 30, 0.1);
537
- -webkit-animation: highlight 400ms linear 1;
538
- -moz-animation: highlight 400ms linear 1;
539
- animation: highlight 400ms linear 1;
540
- }
541
-
542
- /* REPL shell */
543
- .be-console {
544
- padding: 0 1px 10px 1px;
545
- border-bottom-left-radius: 2px;
546
- border-bottom-right-radius: 2px;
547
- }
548
-
549
- .be-console pre {
550
- padding: 10px 10px 0 10px;
551
- max-height: 400px;
552
- overflow-x: none;
553
- overflow-y: auto;
554
- margin-bottom: -3px;
555
- word-wrap: break-word;
556
- white-space: pre-wrap;
557
- }
558
-
559
- /* .command-line > span + input */
560
- .be-console .command-line {
561
- display: table;
562
- width: 100%;
563
- }
564
-
565
- .be-console .command-line span,
566
- .be-console .command-line input {
567
- display: table-cell;
568
- }
569
-
570
- .be-console .command-line span {
571
- width: 1%;
572
- padding-right: 5px;
573
- padding-left: 10px;
574
- white-space: pre;
575
- }
576
-
577
- .be-console .command-line input {
578
- width: 99%;
579
- }
580
-
581
- /* Input box */
582
- .be-console input,
583
- .be-console input:focus {
584
- outline: 0;
585
- border: 0;
586
- padding: 0;
587
- background: transparent;
588
- margin: 0;
589
- }
590
-
591
- /* Hint text */
592
- .hint {
593
- margin: 15px 0 20px 0;
594
- font-size: 8pt;
595
- color: #8080a0;
596
- padding-left: 20px;
597
- }
598
- .console-has-been-used .live-console-hint {
599
- display: none;
600
- }
601
-
602
- .hint:before {
603
- content: '\25b2';
604
- margin-right: 5px;
605
- opacity: 0.5;
606
- }
607
-
608
- /* ---------------------------------------------------------------------
609
- * Variable infos
610
- * --------------------------------------------------------------------- */
611
-
612
- .sub {
613
- padding: 10px 0;
614
- margin: 10px 0;
615
- }
616
-
617
- .sub h3 {
618
- color: #39a;
619
- font-size: 1.1em;
620
- margin: 10px 0;
621
- text-shadow: 0 1px 0 rgba(255, 255, 255, 0.6);
622
-
623
- -webkit-font-smoothing: antialiased;
624
- }
625
-
626
- .sub .inset {
627
- overflow-y: auto;
628
- }
629
-
630
- .sub table {
631
- table-layout: fixed;
632
- }
633
-
634
- .sub table td {
635
- border-top: dotted 1px #ddd;
636
- padding: 7px 1px;
637
- }
638
-
639
- .sub table td.name {
640
- width: 150px;
641
-
642
- font-weight: bold;
643
- font-size: 0.8em;
644
- padding-right: 20px;
645
-
646
- word-wrap: break-word;
647
- }
648
-
649
- .sub table td pre {
650
- max-height: 15em;
651
- overflow-y: auto;
652
- }
653
-
654
- .sub table td pre {
655
- width: 100%;
656
-
657
- word-wrap: break-word;
658
- white-space: normal;
659
- }
660
-
661
- /* "(object doesn't support inspect)" */
662
- .sub .unsupported {
663
- font-family: sans-serif;
664
- color: #777;
665
- }
666
-
667
- /* ---------------------------------------------------------------------
668
- * Scrollbar
669
- * --------------------------------------------------------------------- */
670
-
671
- nav.sidebar::-webkit-scrollbar,
672
- .inset pre::-webkit-scrollbar,
673
- .be-console pre::-webkit-scrollbar,
674
- .code::-webkit-scrollbar {
675
- width: 10px;
676
- height: 10px;
677
- }
678
-
679
- .inset pre::-webkit-scrollbar-thumb,
680
- .be-console pre::-webkit-scrollbar-thumb,
681
- .code::-webkit-scrollbar-thumb {
682
- background: #ccc;
683
- border-radius: 5px;
684
- }
685
-
686
- nav.sidebar::-webkit-scrollbar-thumb {
687
- background: rgba(0, 0, 0, 0.0);
688
- border-radius: 5px;
689
- }
690
-
691
- nav.sidebar:hover::-webkit-scrollbar-thumb {
692
- background-color: #999;
693
- background: -webkit-linear-gradient(left, #aaa, #999);
694
- }
695
-
696
- .be-console pre:hover::-webkit-scrollbar-thumb,
697
- .inset pre:hover::-webkit-scrollbar-thumb,
698
- .code:hover::-webkit-scrollbar-thumb {
699
- background: #888;
700
- }
701
- </style>
9
+ <%== ErrorPageStyle.style_tag(csp_nonce) %>
702
10
 
703
11
  <%# IE8 compatibility crap %>
704
- <script>
12
+ <script nonce="<%= csp_nonce %>">
705
13
  (function() {
706
14
  var elements = ["section", "nav", "header", "footer", "audio"];
707
15
  for (var i = 0; i < elements.length; i++) {
@@ -715,7 +23,7 @@
715
23
  rendered in the host app's layout. Let's empty out the styles of the
716
24
  host app.
717
25
  %>
718
- <script>
26
+ <script nonce="<%= csp_nonce %>">
719
27
  if (window.Turbolinks) {
720
28
  for(var i=0; i < document.styleSheets.length; i++) {
721
29
  if(document.styleSheets[i].href)
@@ -740,6 +48,15 @@
740
48
  }
741
49
  </script>
742
50
 
51
+ <p class='no-inline-style-notice'>
52
+ <strong>
53
+ Better Errors can't apply inline style<span class='no-javascript-notice'> (or run Javascript)</span>,
54
+ possibly because you have a Content Security Policy along with Turbolinks.
55
+ But you can
56
+ <a href='/__better_errors' target="_blank">open the interactive console in a new tab/window</a>.
57
+ </strong>
58
+ </p>
59
+
743
60
  <div class='top'>
744
61
  <header class="exception">
745
62
  <h2><strong><%= exception_type %></strong> <span>at <%= request_path %></span></h2>
@@ -786,21 +103,37 @@
786
103
  </ul>
787
104
  </nav>
788
105
 
789
- <% backtrace_frames.each_with_index do |frame, index| %>
790
- <div class="frame_info" id="frame_info_<%= index %>" style="display:none;"></div>
791
- <% end %>
106
+ <div class="frameInfos">
107
+ <div class="frame_info current" data-frame-idx="0">
108
+ <p class='no-javascript-notice'>
109
+ Better Errors can't run Javascript here<span class='no-inline-style-notice'> (or apply inline style)</span>,
110
+ possibly because you have a Content Security Policy along with Turbolinks.
111
+ But you can
112
+ <a href='/__better_errors' target="_blank">open the interactive console in a new tab/window</a>.
113
+ </p>
114
+ <!-- this is enough information to show something in case JS doesn't get to load -->
115
+ <%== ErrorPage.render_template('variable_info', first_frame_variable_info) %>
116
+ </div>
117
+ </div>
792
118
  </section>
793
119
  </body>
794
- <script>
120
+ <script nonce="<%= csp_nonce %>">
795
121
  (function() {
796
122
 
797
123
  var OID = "<%= id %>";
798
124
  var csrfToken = "<%= csrf_token %>";
799
125
 
800
126
  var previousFrame = null;
801
- var previousFrameInfo = null;
802
127
  var allFrames = document.querySelectorAll("ul.frames li");
803
- var allFrameInfos = document.querySelectorAll(".frame_info");
128
+ var frameInfos = document.querySelector(".frameInfos");
129
+
130
+ document.querySelector('body').classList.remove("better-errors-javascript-not-loaded");
131
+ document.querySelector('body').classList.add("better-errors-javascript-loaded");
132
+
133
+ var noJSNotices = document.querySelectorAll('.no-javascript-notice');
134
+ for(var i = 0; i < noJSNotices.length; i++) {
135
+ noJSNotices[i].remove();
136
+ }
804
137
 
805
138
  function apiCall(method, opts, cb) {
806
139
  var req = new XMLHttpRequest();
@@ -916,7 +249,7 @@
916
249
  self.writeOutput(response.error + "\n");
917
250
  }
918
251
  self.writeOutput(self._prompt + " ");
919
- self.writeRawOutput(response.highlighted_input + "\n");
252
+ self.writeRawOutput("<span class='syntax-highlighted'>" + response.highlighted_input + "</span>\n");
920
253
  self.writeOutput(response.result);
921
254
  self.setPrompt(response.prompt);
922
255
  self.setInput(response.prefilled_input);
@@ -974,17 +307,25 @@
974
307
  };
975
308
 
976
309
  function switchTo(el) {
977
- if(previousFrameInfo) previousFrameInfo.style.display = "none";
978
- previousFrameInfo = el;
310
+ var currentFrameInfo = document.querySelectorAll('.frame_info.current');
311
+ for(var i = 0; i < currentFrameInfo.length; i++) {
312
+ currentFrameInfo[i].className = "frame_info";
313
+ }
979
314
 
980
- el.style.display = "block";
315
+ el.className = "frame_info current";
981
316
 
982
317
  var replInput = el.querySelector('.be-console input');
983
318
  if (replInput) replInput.focus();
984
319
  }
985
320
 
986
321
  function selectFrameInfo(index) {
987
- var el = allFrameInfos[index];
322
+ var el = document.querySelector(".frame_info[data-frame-idx='" + index + "']")
323
+ if (!el) {
324
+ el = document.createElement("div");
325
+ el.className = "frame_info";
326
+ el.setAttribute('data-frame-idx', index);
327
+ frameInfos.appendChild(el);
328
+ }
988
329
  if(el) {
989
330
  if (el.loaded) {
990
331
  return switchTo(el);