rubydojo 0.1.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.
@@ -0,0 +1,738 @@
1
+ @import url('https://fonts.googleapis.com/css2?family=Fira+Code:wght@400;600&family=Inter:wght@400;500;600;700&family=Outfit:wght@400;600;700;800&display=swap');
2
+
3
+ :root {
4
+ /* Royal Red and Beige Theme Colors */
5
+ --bg-main: #fdfbf7; /* Elegant Cream */
6
+ --bg-card: #f5efe6; /* Warm Sand */
7
+ --bg-card-hover: #eae2d5; /* Darker Warm Sand */
8
+ --border-color: #e2d7c5; /* Soft Clay Border */
9
+
10
+ --color-primary: #991b1b; /* Royal Ruby Red (used sparingly) */
11
+ --color-primary-glow: rgba(153, 27, 27, 0.15);
12
+ --color-secondary: #7c2d12; /* Deep Amber/Bronze */
13
+ --color-secondary-glow: rgba(124, 45, 18, 0.15);
14
+
15
+ --color-success: #166534; /* Forest Green */
16
+ --color-success-glow: rgba(22, 101, 52, 0.15);
17
+ --color-danger: #b91c1c; /* Ruby Red Danger */
18
+
19
+ --text-main: #292524; /* Stone 900 / Charcoal */
20
+ --text-muted: #78716c; /* Stone 500 / Muted Brown-Grey */
21
+ --text-bright: #1c1917; /* Stone 950 / Off-black */
22
+
23
+ /* Terminal Specific (Dark Chestnut parchment style) */
24
+ --bg-terminal: #1c1917;
25
+ --text-terminal: #f5efe6;
26
+
27
+ --font-title: 'Outfit', -apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, Helvetica, Arial, sans-serif;
28
+ --font-body: 'Inter', -apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, Helvetica, Arial, sans-serif;
29
+ --font-mono: 'Fira Code', monospace;
30
+ }
31
+
32
+ * {
33
+ box-sizing: border-box;
34
+ margin: 0;
35
+ padding: 0;
36
+ }
37
+
38
+ body {
39
+ background-color: var(--bg-main);
40
+ color: var(--text-main);
41
+ font-family: var(--font-body);
42
+ line-height: 1.6;
43
+ -webkit-font-smoothing: antialiased;
44
+ }
45
+
46
+ h1, h2, h3, h4, h5, h6 {
47
+ font-family: var(--font-title);
48
+ color: var(--text-bright);
49
+ font-weight: 700;
50
+ }
51
+
52
+ a {
53
+ color: var(--color-primary);
54
+ text-decoration: none;
55
+ transition: all 0.2s ease;
56
+ }
57
+
58
+ a:hover {
59
+ color: var(--color-secondary);
60
+ text-shadow: 0 0 8px var(--color-secondary-glow);
61
+ }
62
+
63
+ /* Scrollbars */
64
+ ::-webkit-scrollbar {
65
+ width: 8px;
66
+ height: 8px;
67
+ }
68
+ ::-webkit-scrollbar-track {
69
+ background: var(--bg-main);
70
+ }
71
+ ::-webkit-scrollbar-thumb {
72
+ background: var(--border-color);
73
+ border-radius: 4px;
74
+ }
75
+ ::-webkit-scrollbar-thumb:hover {
76
+ background: var(--color-primary);
77
+ }
78
+
79
+ /* Glassmorphism Header */
80
+ .app-header {
81
+ position: sticky;
82
+ top: 0;
83
+ z-index: 50;
84
+ background: rgba(253, 251, 247, 0.9);
85
+ backdrop-filter: blur(12px);
86
+ -webkit-backdrop-filter: blur(12px);
87
+ border-bottom: 1px solid var(--border-color);
88
+ padding: 0.8rem 2rem;
89
+ display: flex;
90
+ justify-content: space-between;
91
+ align-items: center;
92
+ }
93
+
94
+ .logo {
95
+ display: flex;
96
+ align-items: center;
97
+ gap: 0.75rem;
98
+ font-family: var(--font-title);
99
+ font-size: 1.5rem;
100
+ font-weight: 800;
101
+ color: var(--color-primary) !important;
102
+ text-shadow: none !important;
103
+ }
104
+
105
+ .logo:hover {
106
+ color: var(--color-secondary) !important;
107
+ }
108
+
109
+ .logo-icon {
110
+ width: 2rem;
111
+ height: 2rem;
112
+ background: linear-gradient(135deg, var(--color-primary), var(--color-secondary));
113
+ border-radius: 0.5rem;
114
+ display: flex;
115
+ align-items: center;
116
+ justify-content: center;
117
+ color: white;
118
+ font-weight: bold;
119
+ font-size: 1.1rem;
120
+ box-shadow: 0 0 10px var(--color-primary-glow);
121
+ }
122
+
123
+ .nav-links {
124
+ display: flex;
125
+ gap: 1.5rem;
126
+ align-items: center;
127
+ }
128
+
129
+ .nav-btn {
130
+ padding: 0.5rem 1rem;
131
+ border-radius: 0.375rem;
132
+ font-weight: 500;
133
+ transition: all 0.2s;
134
+ cursor: pointer;
135
+ border: 1px solid transparent;
136
+ }
137
+
138
+ .nav-btn.primary {
139
+ background: linear-gradient(135deg, var(--color-primary), #7f1d1d);
140
+ color: white !important;
141
+ box-shadow: 0 4px 12px var(--color-primary-glow);
142
+ }
143
+
144
+ .nav-btn.primary:hover {
145
+ transform: translateY(-1px);
146
+ box-shadow: 0 6px 16px rgba(153, 27, 27, 0.4);
147
+ color: white !important;
148
+ }
149
+
150
+ .nav-btn.secondary {
151
+ border-color: var(--border-color);
152
+ color: var(--text-main) !important;
153
+ background: transparent;
154
+ }
155
+
156
+ .nav-btn.secondary:hover {
157
+ background: rgba(153, 27, 27, 0.04);
158
+ border-color: var(--color-primary);
159
+ }
160
+
161
+ /* Container */
162
+ .container {
163
+ max-width: 1100px;
164
+ margin: 0 auto;
165
+ padding: 2rem;
166
+ }
167
+
168
+ /* Dashboard / Roadmap Styles */
169
+ .hero-section {
170
+ text-align: center;
171
+ margin-bottom: 3rem;
172
+ animation: fadeIn 0.8s ease-out;
173
+ }
174
+
175
+ .hero-title {
176
+ font-size: 2.75rem;
177
+ margin-bottom: 0.5rem;
178
+ letter-spacing: -0.025em;
179
+ color: var(--text-bright);
180
+ }
181
+
182
+ .hero-subtitle {
183
+ color: var(--text-muted);
184
+ font-size: 1.1rem;
185
+ max-width: 600px;
186
+ margin: 0 auto 1.5rem auto;
187
+ }
188
+
189
+ .progress-container {
190
+ max-width: 500px;
191
+ margin: 0 auto;
192
+ background: var(--bg-card);
193
+ border: 1px solid var(--border-color);
194
+ padding: 1.25rem;
195
+ border-radius: 0.75rem;
196
+ }
197
+
198
+ .progress-text {
199
+ display: flex;
200
+ justify-content: space-between;
201
+ margin-bottom: 0.5rem;
202
+ font-size: 0.9rem;
203
+ color: var(--text-main);
204
+ font-weight: 500;
205
+ }
206
+
207
+ .progress-bar-bg {
208
+ background: rgba(0, 0, 0, 0.08);
209
+ height: 0.75rem;
210
+ border-radius: 9999px;
211
+ overflow: hidden;
212
+ }
213
+
214
+ .progress-bar-fill {
215
+ background: linear-gradient(90deg, var(--color-primary), var(--color-secondary));
216
+ height: 100%;
217
+ border-radius: 9999px;
218
+ box-shadow: 0 0 5px var(--color-primary-glow);
219
+ transition: width 0.5s ease-out;
220
+ }
221
+
222
+ /* The Roadmap Path */
223
+ .roadmap-path {
224
+ position: relative;
225
+ display: flex;
226
+ flex-direction: column;
227
+ align-items: center;
228
+ gap: 4rem;
229
+ margin-top: 4rem;
230
+ padding-bottom: 6rem;
231
+ }
232
+
233
+ .roadmap-line {
234
+ position: absolute;
235
+ top: 0;
236
+ bottom: 0;
237
+ width: 4px;
238
+ background: linear-gradient(to bottom, var(--color-primary), var(--color-secondary), var(--border-color));
239
+ z-index: 1;
240
+ }
241
+
242
+ .roadmap-node {
243
+ position: relative;
244
+ z-index: 2;
245
+ width: 100%;
246
+ max-width: 550px;
247
+ display: flex;
248
+ align-items: center;
249
+ opacity: 0;
250
+ animation: slideUp 0.6s ease-out forwards;
251
+ }
252
+
253
+ .roadmap-node:nth-child(even) {
254
+ flex-direction: row-reverse;
255
+ }
256
+
257
+ .node-card {
258
+ background: var(--bg-card);
259
+ border: 1px solid var(--border-color);
260
+ border-radius: 1rem;
261
+ padding: 1.5rem;
262
+ width: calc(100% - 2.5rem);
263
+ box-shadow: 0 4px 15px -3px rgba(124, 45, 18, 0.05);
264
+ transition: all 0.3s cubic-bezier(0.4, 0, 0.2, 1);
265
+ display: flex;
266
+ flex-direction: column;
267
+ gap: 0.5rem;
268
+ position: relative;
269
+ }
270
+
271
+ .node-card::before {
272
+ content: '';
273
+ position: absolute;
274
+ top: 50%;
275
+ right: -0.5rem;
276
+ transform: translateY(-50%) rotate(45deg);
277
+ width: 1rem;
278
+ height: 1rem;
279
+ background: var(--bg-card);
280
+ border-top: 1px solid var(--border-color);
281
+ border-right: 1px solid var(--border-color);
282
+ z-index: -1;
283
+ }
284
+
285
+ .roadmap-node:nth-child(even) .node-card::before {
286
+ left: -0.5rem;
287
+ right: auto;
288
+ border-top: none;
289
+ border-right: none;
290
+ border-bottom: 1px solid var(--border-color);
291
+ border-left: 1px solid var(--border-color);
292
+ }
293
+
294
+ .node-card:hover {
295
+ transform: translateY(-4px);
296
+ border-color: var(--color-primary);
297
+ box-shadow: 0 10px 25px -5px var(--color-primary-glow);
298
+ }
299
+
300
+ .node-card.completed {
301
+ border-color: var(--color-success);
302
+ }
303
+ .node-card.completed:hover {
304
+ box-shadow: 0 10px 25px -5px var(--color-success-glow);
305
+ }
306
+
307
+ .node-badge {
308
+ font-family: var(--font-title);
309
+ font-size: 0.75rem;
310
+ text-transform: uppercase;
311
+ letter-spacing: 0.05em;
312
+ color: var(--color-secondary);
313
+ font-weight: 700;
314
+ }
315
+
316
+ .node-card.completed .node-badge {
317
+ color: var(--color-success);
318
+ }
319
+
320
+ .node-title {
321
+ font-size: 1.35rem;
322
+ font-weight: 700;
323
+ margin-bottom: 0.25rem;
324
+ color: var(--text-bright);
325
+ }
326
+
327
+ .node-description {
328
+ color: var(--text-muted);
329
+ font-size: 0.9rem;
330
+ }
331
+
332
+ .node-footer {
333
+ display: flex;
334
+ justify-content: space-between;
335
+ align-items: center;
336
+ margin-top: 1rem;
337
+ }
338
+
339
+ .node-status-text {
340
+ font-size: 0.85rem;
341
+ font-weight: 500;
342
+ display: flex;
343
+ align-items: center;
344
+ gap: 0.35rem;
345
+ }
346
+
347
+ .status-indicator {
348
+ width: 8px;
349
+ height: 8px;
350
+ border-radius: 50%;
351
+ display: inline-block;
352
+ }
353
+
354
+ .status-indicator.pending {
355
+ background: var(--text-muted);
356
+ }
357
+ .status-indicator.completed {
358
+ background: var(--color-success);
359
+ box-shadow: 0 0 6px var(--color-success);
360
+ }
361
+
362
+ .node-circle {
363
+ width: 3rem;
364
+ height: 3rem;
365
+ border-radius: 50%;
366
+ background: var(--bg-card);
367
+ border: 4px solid var(--border-color);
368
+ color: var(--text-main);
369
+ display: flex;
370
+ align-items: center;
371
+ justify-content: center;
372
+ font-weight: bold;
373
+ font-family: var(--font-title);
374
+ font-size: 1.15rem;
375
+ z-index: 10;
376
+ box-shadow: 0 2px 5px rgba(0,0,0,0.05);
377
+ transition: all 0.3s;
378
+ }
379
+
380
+ .roadmap-node:hover .node-circle {
381
+ border-color: var(--color-primary);
382
+ background: var(--color-primary);
383
+ color: white;
384
+ box-shadow: 0 0 10px var(--color-primary-glow);
385
+ }
386
+
387
+ .roadmap-node.completed .node-circle {
388
+ border-color: var(--color-success);
389
+ background: rgba(22, 101, 52, 0.05);
390
+ color: var(--color-success);
391
+ }
392
+
393
+ .roadmap-node.completed:hover .node-circle {
394
+ background: var(--color-success);
395
+ color: white;
396
+ box-shadow: 0 0 10px var(--color-success-glow);
397
+ }
398
+
399
+ /* Lesson Show Split-Pane Layout */
400
+ .lesson-layout {
401
+ display: grid;
402
+ grid-template-columns: 1.1fr 0.9fr;
403
+ height: calc(100vh - 64px); /* Full height minus header */
404
+ overflow: hidden;
405
+ }
406
+
407
+ .instruction-pane {
408
+ background: var(--bg-main);
409
+ border-right: 1px solid var(--border-color);
410
+ overflow-y: auto;
411
+ padding: 2.5rem;
412
+ }
413
+
414
+ .back-link {
415
+ display: flex;
416
+ align-items: center;
417
+ gap: 0.5rem;
418
+ margin-bottom: 2rem;
419
+ font-size: 0.9rem;
420
+ color: var(--text-muted);
421
+ }
422
+ .back-link:hover {
423
+ color: var(--color-primary);
424
+ }
425
+
426
+ .markdown-content {
427
+ font-size: 1rem;
428
+ line-height: 1.7;
429
+ }
430
+
431
+ .markdown-content h1 {
432
+ font-size: 2.25rem;
433
+ margin-bottom: 1rem;
434
+ color: var(--color-primary);
435
+ }
436
+
437
+ .markdown-content h2 {
438
+ font-size: 1.4rem;
439
+ margin-top: 2rem;
440
+ margin-bottom: 0.75rem;
441
+ border-bottom: 1px solid var(--border-color);
442
+ padding-bottom: 0.5rem;
443
+ color: var(--color-secondary);
444
+ }
445
+
446
+ .markdown-content p {
447
+ margin-bottom: 1.25rem;
448
+ color: var(--text-main);
449
+ }
450
+
451
+ .markdown-content code {
452
+ font-family: var(--font-mono);
453
+ background: rgba(153, 27, 27, 0.05);
454
+ padding: 0.2rem 0.4rem;
455
+ border-radius: 0.25rem;
456
+ font-size: 0.9rem;
457
+ border: 1px solid rgba(153, 27, 27, 0.1);
458
+ color: var(--color-primary);
459
+ }
460
+
461
+ .markdown-content pre {
462
+ background: var(--bg-card);
463
+ border: 1px solid var(--border-color);
464
+ padding: 1rem;
465
+ border-radius: 0.5rem;
466
+ overflow-x: auto;
467
+ margin-bottom: 1.5rem;
468
+ }
469
+
470
+ .markdown-content pre code {
471
+ background: transparent;
472
+ padding: 0;
473
+ border: none;
474
+ color: var(--text-main);
475
+ }
476
+
477
+ .markdown-content ul, .markdown-content ol {
478
+ margin-bottom: 1.5rem;
479
+ padding-left: 1.5rem;
480
+ }
481
+
482
+ .markdown-content li {
483
+ margin-bottom: 0.5rem;
484
+ color: var(--text-main);
485
+ }
486
+
487
+ /* Editor & Compiler Pane - FIXING HEIGHT STABILITY */
488
+ .workspace-pane {
489
+ display: flex;
490
+ flex-direction: column;
491
+ height: 100%;
492
+ background: #fdfbf7;
493
+ overflow: hidden; /* Prevent parent container from expanding beyond viewport! */
494
+ }
495
+
496
+ .pane-header {
497
+ background: var(--bg-card);
498
+ padding: 0.75rem 1.5rem;
499
+ border-bottom: 1px solid var(--border-color);
500
+ display: flex;
501
+ justify-content: space-between;
502
+ align-items: center;
503
+ flex-shrink: 0; /* Header height remains static */
504
+ }
505
+
506
+ .pane-title {
507
+ font-family: var(--font-title);
508
+ font-size: 0.9rem;
509
+ font-weight: 600;
510
+ color: var(--text-main);
511
+ display: flex;
512
+ align-items: center;
513
+ gap: 0.5rem;
514
+ }
515
+
516
+ /* Editor Container fills remaining viewport space above terminal */
517
+ .editor-container {
518
+ flex: 1; /* Grow and shrink dynamically */
519
+ min-height: 0; /* Crucial for nested scroll container to function */
520
+ position: relative;
521
+ border-bottom: 1px solid var(--border-color);
522
+ font-family: var(--font-mono);
523
+ }
524
+
525
+ /* Custom Light-Beige CodeMirror Styling */
526
+ .CodeMirror {
527
+ height: 100% !important;
528
+ font-size: 0.95rem;
529
+ background: #fdfbf7 !important;
530
+ color: var(--text-main) !important;
531
+ }
532
+
533
+ .CodeMirror-gutters {
534
+ background: var(--bg-card) !important;
535
+ border-right: 1px solid var(--border-color) !important;
536
+ }
537
+
538
+ .CodeMirror-linenumber {
539
+ color: var(--text-muted) !important;
540
+ }
541
+
542
+ .CodeMirror-cursor {
543
+ border-left: 2px solid var(--color-primary) !important;
544
+ }
545
+
546
+ .CodeMirror-selected {
547
+ background: rgba(153, 27, 27, 0.1) !important;
548
+ }
549
+
550
+ /* Simulated Terminal - STATIC FIXED HEIGHT & OVERFLOW CONFIG */
551
+ .terminal-container {
552
+ height: 220px; /* FIXED STATIC HEIGHT - NEVER GROWS */
553
+ background: var(--bg-terminal);
554
+ display: flex;
555
+ flex-direction: column;
556
+ flex-shrink: 0; /* DO NOT ALLOW GROWING OR SHRINKING */
557
+ border-bottom: 1px solid var(--border-color);
558
+ }
559
+
560
+ .terminal-header {
561
+ background: #292524;
562
+ border-bottom: 1px solid #44403c;
563
+ padding: 0.5rem 1.5rem;
564
+ font-size: 0.8rem;
565
+ font-weight: 600;
566
+ font-family: var(--font-title);
567
+ color: #a8a29e;
568
+ display: flex;
569
+ justify-content: space-between;
570
+ flex-shrink: 0;
571
+ }
572
+
573
+ .terminal-body {
574
+ flex: 1;
575
+ padding: 1rem 1.5rem;
576
+ overflow-y: auto; /* SCROLL CONTENT INTERNALLY */
577
+ font-family: var(--font-mono);
578
+ font-size: 0.875rem;
579
+ color: var(--text-terminal);
580
+ display: flex;
581
+ flex-direction: column;
582
+ gap: 0.5rem;
583
+ }
584
+
585
+ .terminal-line {
586
+ display: flex;
587
+ gap: 0.5rem;
588
+ }
589
+
590
+ .terminal-line.output {
591
+ color: #fff;
592
+ white-space: pre-wrap;
593
+ }
594
+
595
+ .terminal-line.success {
596
+ color: #4ade80; /* Brighter green for terminal contrast */
597
+ font-weight: bold;
598
+ }
599
+
600
+ .terminal-line.error {
601
+ color: #f87171; /* Brighter red for terminal contrast */
602
+ white-space: pre-wrap;
603
+ }
604
+
605
+ .terminal-line.system {
606
+ color: #a8a29e;
607
+ }
608
+
609
+ .prompt-symbol {
610
+ color: var(--color-danger);
611
+ font-weight: bold;
612
+ user-select: none;
613
+ }
614
+
615
+ /* Workspace Actions - PERMANENTLY ANCHORED AT BOTTOM */
616
+ .workspace-actions {
617
+ background: var(--bg-card);
618
+ padding: 1rem 1.5rem;
619
+ display: flex;
620
+ gap: 1rem;
621
+ justify-content: flex-end;
622
+ border-top: 1px solid var(--border-color);
623
+ flex-shrink: 0; /* Actions panel height remains static */
624
+ }
625
+
626
+ .btn {
627
+ display: inline-flex;
628
+ align-items: center;
629
+ gap: 0.5rem;
630
+ padding: 0.65rem 1.25rem;
631
+ border-radius: 0.375rem;
632
+ font-weight: 600;
633
+ font-size: 0.9rem;
634
+ cursor: pointer;
635
+ transition: all 0.2s;
636
+ border: 1px solid transparent;
637
+ }
638
+
639
+ .btn-secondary {
640
+ background: transparent;
641
+ border-color: var(--border-color);
642
+ color: var(--text-main);
643
+ }
644
+ .btn-secondary:hover {
645
+ background: rgba(0, 0, 0, 0.03);
646
+ border-color: var(--text-muted);
647
+ }
648
+
649
+ .btn-primary {
650
+ background: linear-gradient(135deg, var(--color-primary), #7f1d1d);
651
+ color: white;
652
+ box-shadow: 0 4px 10px var(--color-primary-glow);
653
+ }
654
+ .btn-primary:hover {
655
+ transform: translateY(-1px);
656
+ box-shadow: 0 6px 14px rgba(153, 27, 27, 0.3);
657
+ }
658
+
659
+ .btn-success {
660
+ background: linear-gradient(135deg, var(--color-success), #14532d);
661
+ color: white;
662
+ box-shadow: 0 4px 10px var(--color-success-glow);
663
+ }
664
+ .btn-success:hover {
665
+ transform: translateY(-1px);
666
+ box-shadow: 0 6px 14px rgba(22, 101, 52, 0.3);
667
+ }
668
+
669
+ /* Animations */
670
+ @keyframes fadeIn {
671
+ from { opacity: 0; }
672
+ to { opacity: 1; }
673
+ }
674
+
675
+ @keyframes slideUp {
676
+ from {
677
+ opacity: 0;
678
+ transform: translateY(20px);
679
+ }
680
+ to {
681
+ opacity: 1;
682
+ transform: translateY(0);
683
+ }
684
+ }
685
+
686
+ .animate-fade-in {
687
+ animation: fadeIn 0.5s ease-out;
688
+ }
689
+
690
+ /* Success Overlay (Lesson completion modal/banner) */
691
+ .success-banner {
692
+ background: rgba(22, 101, 52, 0.05);
693
+ border: 1px solid var(--color-success);
694
+ border-radius: 0.5rem;
695
+ padding: 1rem;
696
+ margin-top: 1.5rem;
697
+ display: flex;
698
+ align-items: center;
699
+ gap: 0.75rem;
700
+ color: var(--color-success);
701
+ font-weight: 500;
702
+ animation: slideUp 0.4s ease-out;
703
+ }
704
+
705
+ .success-banner-icon {
706
+ font-size: 1.5rem;
707
+ }
708
+
709
+ /* Loading Spinner */
710
+ .spinner {
711
+ width: 1rem;
712
+ height: 1rem;
713
+ border: 2px solid rgba(255, 255, 255, 0.2);
714
+ border-radius: 50%;
715
+ border-top-color: white;
716
+ animation: spin 0.8s linear infinite;
717
+ }
718
+
719
+ @keyframes spin {
720
+ to { transform: rotate(360deg); }
721
+ }
722
+
723
+ /* Custom hints styling */
724
+ .hint-box {
725
+ background: rgba(124, 45, 18, 0.03);
726
+ border: 1px solid rgba(124, 45, 18, 0.15);
727
+ border-radius: 0.5rem;
728
+ padding: 1rem;
729
+ margin-top: 1.5rem;
730
+ color: var(--color-secondary);
731
+ font-size: 0.9rem;
732
+ display: none; /* JS toggles this */
733
+ animation: slideUp 0.3s ease-out;
734
+ }
735
+
736
+ .hint-box.visible {
737
+ display: block;
738
+ }
@@ -0,0 +1,4 @@
1
+ module Rubydojo
2
+ class ApplicationController < ActionController::Base
3
+ end
4
+ end