-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathredis-masterclass-tutorial.html
More file actions
255 lines (215 loc) · 12.9 KB
/
Copy pathredis-masterclass-tutorial.html
File metadata and controls
255 lines (215 loc) · 12.9 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Redis Masterclass 🔥</title>
<!-- Google Fonts -->
<link rel="preconnect" href="https://fonts.googleapis.com">
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
<link href="https://fonts.googleapis.com/css2?family=Plus+Jakarta+Sans:wght@300;400;500;600;700;800&family=JetBrains+Mono:wght@400;500&display=swap" rel="stylesheet">
<!-- Highlight.js for Code Formatting -->
<link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/highlight.js/11.8.0/styles/github-dark.min.css">
<script src="https://cdnjs.cloudflare.com/ajax/libs/highlight.js/11.8.0/highlight.min.js"></script>
<script>hljs.highlightAll();</script>
<style>
:root {
--bg-color: #0c0a0a;
--surface-color: #1a1616;
--primary-color: #ef4444; /* Redis Red */
--primary-glow: rgba(239, 68, 68, 0.4);
--text-main: #f8fafc;
--text-muted: #9ca3af;
--border-color: rgba(255, 255, 255, 0.08);
--card-border: rgba(255, 255, 255, 0.1);
}
* { margin: 0; padding: 0; box-sizing: border-box; }
html { scroll-behavior: smooth; }
body {
font-family: 'Plus Jakarta Sans', sans-serif;
background-color: var(--bg-color); color: var(--text-main); line-height: 1.6;
background-image:
radial-gradient(at 0% 0%, rgba(239, 68, 68, 0.15) 0px, transparent 50%),
radial-gradient(at 100% 100%, rgba(220, 38, 38, 0.1) 0px, transparent 50%);
background-attachment: fixed; min-height: 100vh;
}
.layout { display: flex; gap: 2.5rem; max-width: 1400px; margin: 0 auto; padding: 3rem 2rem; }
/* Sidebar Styles (Reused) */
.sidebar {
width: 280px; flex-shrink: 0; position: sticky; top: 3rem; max-height: calc(100vh - 6rem); overflow-y: auto;
background: rgba(26, 22, 22, 0.8); border: 1px solid var(--card-border); border-radius: 16px; padding: 1.5rem;
backdrop-filter: blur(12px);
}
.sidebar h3 {
margin-bottom: 1rem; font-size: 1.1rem; text-transform: uppercase; letter-spacing: 1.5px;
color: var(--primary-color); border-bottom: 1px solid var(--card-border); padding-bottom: 1rem;
}
.sidebar ul { list-style: none; }
.sidebar li { margin-bottom: 0.3rem; }
.nav-section {
font-size: 0.85rem; text-transform: uppercase; letter-spacing: 1px; color: var(--text-muted);
margin: 1.5rem 0 0.5rem 0; padding-left: 0.5rem; font-weight: 700;
}
.sidebar a {
text-decoration: none; color: var(--text-muted); display: block; padding: 0.5rem 1rem;
border-radius: 8px; transition: all 0.3s ease; font-size: 0.95rem; font-weight: 500;
}
.sidebar a.active {
background: rgba(239, 68, 68, 0.2); color: #fff; border-left: 3px solid var(--primary-color); border-radius: 4px 8px 8px 4px;
}
.sidebar a:hover:not(.active) { background: rgba(239, 68, 68, 0.15); color: var(--primary-color); transform: translateX(5px); }
.main-content { flex: 1; min-width: 0; }
header { text-align: center; margin-bottom: 3rem; }
h1 {
font-size: 3rem; font-weight: 800; margin-bottom: 1rem;
background: linear-gradient(135deg, var(--primary-color) 0%, #fca5a5 100%);
-webkit-background-clip: text; -webkit-text-fill-color: transparent; text-shadow: 0 0 40px var(--primary-glow);
}
.subtitle { font-size: 1.2rem; color: var(--text-muted); }
/* Content Blocks */
.content-card {
background: rgba(26, 22, 22, 0.6); border: 1px solid var(--card-border);
border-radius: 16px; padding: 2.5rem; margin-bottom: 2rem; backdrop-filter: blur(10px);
box-shadow: 0 20px 40px -20px rgba(0, 0, 0, 0.5);
}
h2 { font-size: 1.8rem; margin-bottom: 1.5rem; display: flex; align-items: center; gap: 0.5rem; color: #fff; border-bottom: 1px solid var(--border-color); padding-bottom: 1rem; }
h3 { font-size: 1.3rem; margin: 1.5rem 0 1rem; color: #e2e8f0; }
p { margin-bottom: 1rem; font-size: 1.1rem; color: #c9d1d9; }
ul { margin-left: 1.5rem; margin-bottom: 1rem; color: #c9d1d9; }
li { margin-bottom: 0.5rem; }
.explanation { background: rgba(239, 68, 68, 0.1); border-left: 4px solid var(--primary-color); padding: 1rem 1.5rem; border-radius: 0 8px 8px 0; margin: 1.5rem 0; }
.explanation p { margin-bottom: 0; color: #e2e8f0; }
pre { background: #010409 !important; border: 1px solid var(--border-color); border-radius: 12px; padding: 1.5rem !important; margin: 1.5rem 0; overflow-x: auto; box-shadow: 0 10px 30px rgba(0,0,0,0.5); }
code { font-family: 'JetBrains Mono', monospace !important; font-size: 0.95rem; line-height: 1.5; }
.diagram { font-family: 'JetBrains Mono', monospace; background: #050505; color: #fca5a5; padding: 1.5rem; border-radius: 12px; border: 1px solid var(--primary-color); box-shadow: 0 0 20px rgba(239, 68, 68, 0.1); overflow-x: auto; white-space: pre; line-height: 1.4; margin: 1.5rem 0; font-size: 0.9rem; }
.cta-banner { background: linear-gradient(135deg, var(--primary-color) 0%, #b91c1c 100%); padding: 3rem 2rem; border-radius: 16px; text-align: center; margin-top: 3rem; }
.cta-banner h2 { border: none; justify-content: center; }
@media (max-width: 900px) {
.layout { flex-direction: column; }
.sidebar { width: 100%; position: relative; top: 0; max-height: none; margin-bottom: 2rem; }
}
</style>
</head>
<body>
<div class="layout">
<!-- Sidebar Navigation -->
<aside class="sidebar">
<h3>🗂️ Tutorials Link</h3>
<nav>
<ul>
<li><a href="index.html">🏠 Home Hub</a></li>
<li class="nav-section">Databases / Lang</li>
<li><a href="mongodb-conditions-tutorial.html">🍃 MongoDB Class</a></li>
<li><a href="redis-masterclass-tutorial.html" class="active">🔥 Redis</a></li>
<li><a href="typescript-oops-tutorial.html">📘 TS OOPs</a></li>
<li class="nav-section">Architecture</li>
<li><a href="message-queues-tutorial.html">📨 Message Queues</a></li>
<li><a href="notification-system-tutorial.html">🔔 Notifications</a></li>
<li><a href="worker-threads-tutorial.html">⚙️ Node Workers</a></li>
<li><a href="system-design-tutorial.html">🏗️ Sys Design (Part 1)</a></li>
<li><a href="system-design-part2.html">🚀 Sys Design (Part 2)</a></li>
<li class="nav-section">Security & DevOps</li>
<li><a href="github-masterclass-tutorial.html">🐙 Git & GitHub</a></li>
<li><a href="rbac-masterclass-tutorial.html">🔐 RBAC & Auth</a></li>
<li><a href="abac-masterclass-tutorial.html">🛡️ ABAC Policies</a></li>
</ul>
</nav>
</aside>
<!-- Main Content -->
<main class="main-content">
<header>
<h1>Redis Masterclass 🔥</h1>
<p class="subtitle">In-Memory Database, Caching Strategies, and Pub/Sub mechanism.</p>
</header>
<div class="content-card" id="intro">
<h2>1. What is Redis? (In-Memory Magic)</h2>
<p>Normal databases (MongoDB/PostgreSQL) <code>Disk/SSD</code> pe data save karte hain. Jab bhi unse data maango, read/write operation time lagata hai. Lekin <strong>Redis</strong> poora ka poora data tera server ki <strong>RAM</strong> mein store karta hai!</p>
<div class="explanation">
<p>👉 RAM disk se hazaron guna tez hoti hai. Isiliye Redis is used purely as a <strong>Cache</strong> yaani temporary super-fast storage taa ke database pe load na pade.</p>
</div>
</div>
<div class="content-card" id="caching">
<h2>2. Implementing a Cache (NodeJS Example)</h2>
<p>Caching ka flow bohot simple hai: <br>
1. Check if data is in Redis.<br>
2. If Yes (Cache Hit) -> Return instantly.<br>
3. If No (Cache Miss) -> Read from MongoDB -> Store in Redis -> Return to user.</p>
<pre><code class="language-javascript">const fetchUserProfile = async (req, res) => {
const userId = req.params.id;
// 1. Check in Redis first (RAM)
const cachedData = await redisClient.get(`user_profile:${userId}`);
if (cachedData) {
return res.json(JSON.parse(cachedData)); // Lightning Fast ⚡
}
// 2. If not found, fetch from MongoDB (SSD / Disk)
const user = await User.findById(userId);
// 3. Store in Redis for future requests (Expire after 1 hour)
await redisClient.setEx(`user_profile:${userId}`, 3600, JSON.stringify(user));
res.json(user);
};
</code></pre>
</div>
<div class="content-card" id="structures">
<h2>3. Redis Data Structures</h2>
<p>Redis is literally a "Key-Value" store, but the values can be of different data structures:</p>
<h3>A. Strings (General purpose)</h3>
<pre><code class="language-bash">SET username "Salman"
GET username
# Useful for caching JSON blocks or simple strings.</code></pre>
<h3>B. Hashes (Objects)</h3>
<pre><code class="language-bash">HSET user:1 name "Salman" age 25
HGET user:1 name
# Perfect to store JS Objects without stringification overhead.</code></pre>
<h3>C. Sorted Sets (Leaderboards 🏆)</h3>
<p>Gaming leaderboards handle millions of score updates every second. Using SQL `ORDER BY` would crash the database. Redis has a dedicated structure that keeps data SORTED in RAM magically.</p>
<pre><code class="language-bash">ZADD leaderboard 500 "PlayerA"
ZADD leaderboard 1200 "PlayerB"
# Score update hoty hi leaderboard automatic update! (Real-time Fast)
ZREVRANGE leaderboard 0 9 WITHSCORES # Get Top 10 users</code></pre>
<h3>D. Sets (Unique Elements)</h3>
<pre><code class="language-bash">SADD followers:user1 "Ali"
SADD followers:user1 "Hassan"
# Stores only unique IDs. Also allows intersection: "Find Mutual Followers" (SINTER)</code></pre>
</div>
<div class="content-card" id="pubsub">
<h2>4. Redis Pub/Sub (Broadcasting)</h2>
<p>Agar app me 10 alag-alag node.js Servers (Horizontal Scaling) hain. Aur kisi ek server ne "Notification" genmerate ki, toh doosre servers ko kse pta chalega?<br>
Answer: <strong>Redis Publish / Subscribe.</strong></p>
<div class="diagram">
[NodeJS Server 1] --->(PUBLISH 'chat_room')---> [ REDIS MEMORY ]
|
+-------------------------------------+------------------+
v v v
(SUBSCRIBED 'chat_room') (SUBSCRIBED 'chat_room')
[NodeJS Server 2] [NodeJS Server 3]
</div>
<p>Pub/Sub ek radio station jesa hai. Ek banda bolta hai, aur jo jo vo channel sun rahy hn sabko live broadcast hoti h. Great for Chat apps, WebSockets syncing, and Microservices communication.</p>
</div>
<div class="content-card" id="limiting">
<h2>5. Advance Use Case: Rate Limiting</h2>
<p>Kaise kisi user ko 1 minute mai sirf 10 API request karne ki limit deni chahiye? Hum uski IP pakad kr Redis mai gintay hn (since simple RAM operations memory nhi bhrty).</p>
<pre><code class="language-javascript">const rateLimiter = async (req, res, next) => {
const ip = req.ip;
// Increment counter for this IP
const currentRequests = await redis.incr(ip);
if (currentRequests === 1) {
// If it's the first hit, set an expiry of 60 seconds.
await redis.expire(ip, 60);
}
if (currentRequests > 10) {
return res.status(429).json({ error: "Too many requests. Bhai saans lele" });
}
next();
};
</code></pre>
</div>
<div class="cta-banner">
<h2 style="color: white">Redis Ninja Certified! 🥷</h2>
<p style="color: white; margin-top: 10px;">Caching, Rate Limiting & Leaderboards ab tere fingertips par hain!<br><br>
<strong>Keep building fast APIs! 🔥</strong>
</p>
</div>
</main>
</div>
</body>
</html>