opaque_id 1.1.0 → 1.3.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.
- checksums.yaml +4 -4
- data/.release-please-manifest.json +1 -1
- data/CHANGELOG.md +50 -0
- data/CODE_OF_CONDUCT.md +11 -11
- data/README.md +82 -0
- data/docs/.gitignore +5 -0
- data/docs/404.html +25 -0
- data/docs/Gemfile +31 -0
- data/docs/Gemfile.lock +335 -0
- data/docs/_config.yml +162 -0
- data/docs/_data/navigation.yml +132 -0
- data/docs/_includes/footer_custom.html +8 -0
- data/docs/_includes/head_custom.html +67 -0
- data/docs/algorithms.md +409 -0
- data/docs/alphabets.md +521 -0
- data/docs/api-reference.md +594 -0
- data/docs/assets/css/custom.scss +798 -0
- data/docs/assets/images/favicon.svg +17 -0
- data/docs/assets/images/og-image.svg +65 -0
- data/docs/configuration.md +548 -0
- data/docs/development.md +567 -0
- data/docs/getting-started.md +256 -0
- data/docs/index.md +132 -0
- data/docs/installation.md +377 -0
- data/docs/performance.md +488 -0
- data/docs/robots.txt +11 -0
- data/docs/security.md +598 -0
- data/docs/usage.md +414 -0
- data/docs/use-cases.md +569 -0
- data/lib/generators/opaque_id/install_generator.rb +38 -23
- data/lib/opaque_id/version.rb +1 -1
- data/tasks/0003-prd-documentation-site.md +191 -0
- data/tasks/tasks-0003-prd-documentation-site.md +84 -0
- metadata +27 -2
- data/sig/opaque_id.rbs +0 -4
data/docs/alphabets.md
ADDED
@@ -0,0 +1,521 @@
|
|
1
|
+
---
|
2
|
+
layout: default
|
3
|
+
title: Alphabets
|
4
|
+
nav_order: 6
|
5
|
+
description: "Complete guide to built-in alphabets and custom alphabet creation"
|
6
|
+
permalink: /alphabets/
|
7
|
+
---
|
8
|
+
|
9
|
+
# Alphabets
|
10
|
+
|
11
|
+
OpaqueId provides flexible alphabet configuration for generating IDs with different character sets. This guide covers built-in alphabets, custom alphabet creation, and best practices for alphabet selection.
|
12
|
+
|
13
|
+
## Built-in Alphabets
|
14
|
+
|
15
|
+
OpaqueId comes with two pre-configured alphabets optimized for different use cases.
|
16
|
+
|
17
|
+
### ALPHANUMERIC_ALPHABET (Default)
|
18
|
+
|
19
|
+
The default alphabet provides a good balance of security, readability, and URL safety.
|
20
|
+
|
21
|
+
```ruby
|
22
|
+
# Characters: A-Z, a-z, 0-9 (62 characters)
|
23
|
+
# Use case: General purpose, URL-safe
|
24
|
+
# Example output: "V1StGXR8_Z5jdHi6B-myT"
|
25
|
+
|
26
|
+
class User < ApplicationRecord
|
27
|
+
include OpaqueId::Model
|
28
|
+
self.opaque_id_alphabet = OpaqueId::ALPHANUMERIC_ALPHABET
|
29
|
+
end
|
30
|
+
```
|
31
|
+
|
32
|
+
**Characteristics:**
|
33
|
+
|
34
|
+
- **Length**: 62 characters
|
35
|
+
- **Characters**: `ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789`
|
36
|
+
- **URL-safe**: Yes (no special characters)
|
37
|
+
- **Human-readable**: Yes (no confusing characters)
|
38
|
+
- **Performance**: Good (62 characters)
|
39
|
+
|
40
|
+
**Use cases:**
|
41
|
+
|
42
|
+
- General purpose ID generation
|
43
|
+
- Public URLs and user-facing identifiers
|
44
|
+
- APIs and web services
|
45
|
+
- Database primary keys
|
46
|
+
|
47
|
+
### STANDARD_ALPHABET
|
48
|
+
|
49
|
+
The standard alphabet provides the fastest generation speed with 64 characters.
|
50
|
+
|
51
|
+
```ruby
|
52
|
+
# Characters: A-Z, a-z, 0-9, -, _ (64 characters)
|
53
|
+
# Use case: Fastest generation, URL-safe
|
54
|
+
# Example output: "V1StGXR8_Z5jdHi6B-myT"
|
55
|
+
|
56
|
+
class User < ApplicationRecord
|
57
|
+
include OpaqueId::Model
|
58
|
+
self.opaque_id_alphabet = OpaqueId::STANDARD_ALPHABET
|
59
|
+
end
|
60
|
+
```
|
61
|
+
|
62
|
+
**Characteristics:**
|
63
|
+
|
64
|
+
- **Length**: 64 characters
|
65
|
+
- **Characters**: `ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789-_`
|
66
|
+
- **URL-safe**: Yes (includes hyphens and underscores)
|
67
|
+
- **Human-readable**: Yes (minimal special characters)
|
68
|
+
- **Performance**: Best (64 characters, optimized path)
|
69
|
+
|
70
|
+
**Use cases:**
|
71
|
+
|
72
|
+
- High-performance applications
|
73
|
+
- Internal system identifiers
|
74
|
+
- APIs with high throughput
|
75
|
+
- Background job systems
|
76
|
+
|
77
|
+
## Alphabet Comparison
|
78
|
+
|
79
|
+
| Alphabet | Characters | Length | URL-Safe | Performance | Use Case |
|
80
|
+
| ----------------------- | -------------------- | ------ | -------- | ----------- | ---------------- |
|
81
|
+
| `ALPHANUMERIC_ALPHABET` | A-Z, a-z, 0-9 | 62 | ✅ | Good | General purpose |
|
82
|
+
| `STANDARD_ALPHABET` | A-Z, a-z, 0-9, -, \_ | 64 | ✅ | Best | High performance |
|
83
|
+
|
84
|
+
## Custom Alphabets
|
85
|
+
|
86
|
+
Create custom alphabets for specific requirements and use cases.
|
87
|
+
|
88
|
+
### Numeric Only
|
89
|
+
|
90
|
+
Generate numeric-only IDs for order numbers, invoice numbers, etc.
|
91
|
+
|
92
|
+
```ruby
|
93
|
+
class Order < ApplicationRecord
|
94
|
+
include OpaqueId::Model
|
95
|
+
|
96
|
+
# Generate numeric-only IDs
|
97
|
+
self.opaque_id_alphabet = "0123456789"
|
98
|
+
self.opaque_id_length = 10
|
99
|
+
end
|
100
|
+
|
101
|
+
# Example output: "1234567890"
|
102
|
+
```
|
103
|
+
|
104
|
+
**Use cases:**
|
105
|
+
|
106
|
+
- Order numbers
|
107
|
+
- Invoice numbers
|
108
|
+
- Reference numbers
|
109
|
+
- Sequential-looking IDs
|
110
|
+
|
111
|
+
### Hexadecimal
|
112
|
+
|
113
|
+
Generate hexadecimal IDs for API keys, tokens, etc.
|
114
|
+
|
115
|
+
```ruby
|
116
|
+
class ApiKey < ApplicationRecord
|
117
|
+
include OpaqueId::Model
|
118
|
+
|
119
|
+
# Generate hexadecimal IDs
|
120
|
+
self.opaque_id_alphabet = "0123456789abcdef"
|
121
|
+
self.opaque_id_length = 16
|
122
|
+
end
|
123
|
+
|
124
|
+
# Example output: "a1b2c3d4e5f67890"
|
125
|
+
```
|
126
|
+
|
127
|
+
**Use cases:**
|
128
|
+
|
129
|
+
- API keys
|
130
|
+
- Authentication tokens
|
131
|
+
- Session identifiers
|
132
|
+
- Cryptographic keys
|
133
|
+
|
134
|
+
### URL-Safe Characters
|
135
|
+
|
136
|
+
Generate IDs with maximum URL safety.
|
137
|
+
|
138
|
+
```ruby
|
139
|
+
class Article < ApplicationRecord
|
140
|
+
include OpaqueId::Model
|
141
|
+
|
142
|
+
# Generate URL-safe IDs
|
143
|
+
self.opaque_id_alphabet = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789-_"
|
144
|
+
self.opaque_id_length = 8
|
145
|
+
end
|
146
|
+
|
147
|
+
# Example output: "V1StGXR8"
|
148
|
+
```
|
149
|
+
|
150
|
+
**Use cases:**
|
151
|
+
|
152
|
+
- URL slugs
|
153
|
+
- Public identifiers
|
154
|
+
- Social media sharing
|
155
|
+
- Email-friendly IDs
|
156
|
+
|
157
|
+
### Base64-Style
|
158
|
+
|
159
|
+
Generate Base64-style IDs for maximum character diversity.
|
160
|
+
|
161
|
+
```ruby
|
162
|
+
class Document < ApplicationRecord
|
163
|
+
include OpaqueId::Model
|
164
|
+
|
165
|
+
# Generate Base64-style IDs
|
166
|
+
self.opaque_id_alphabet = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/"
|
167
|
+
self.opaque_id_length = 12
|
168
|
+
end
|
169
|
+
|
170
|
+
# Example output: "V1StGXR8_Z5j"
|
171
|
+
```
|
172
|
+
|
173
|
+
**Use cases:**
|
174
|
+
|
175
|
+
- Document identifiers
|
176
|
+
- File references
|
177
|
+
- Binary data representation
|
178
|
+
- High-entropy requirements
|
179
|
+
|
180
|
+
### Uppercase Only
|
181
|
+
|
182
|
+
Generate uppercase-only IDs for better readability.
|
183
|
+
|
184
|
+
```ruby
|
185
|
+
class Product < ApplicationRecord
|
186
|
+
include OpaqueId::Model
|
187
|
+
|
188
|
+
# Generate uppercase-only IDs
|
189
|
+
self.opaque_id_alphabet = "ABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789"
|
190
|
+
self.opaque_id_length = 10
|
191
|
+
end
|
192
|
+
|
193
|
+
# Example output: "V1STGXR8Z5"
|
194
|
+
```
|
195
|
+
|
196
|
+
**Use cases:**
|
197
|
+
|
198
|
+
- Product codes
|
199
|
+
- SKUs
|
200
|
+
- License keys
|
201
|
+
- Human-readable identifiers
|
202
|
+
|
203
|
+
### Lowercase Only
|
204
|
+
|
205
|
+
Generate lowercase-only IDs for consistent formatting.
|
206
|
+
|
207
|
+
```ruby
|
208
|
+
class User < ApplicationRecord
|
209
|
+
include OpaqueId::Model
|
210
|
+
|
211
|
+
# Generate lowercase-only IDs
|
212
|
+
self.opaque_id_alphabet = "abcdefghijklmnopqrstuvwxyz0123456789"
|
213
|
+
self.opaque_id_length = 12
|
214
|
+
end
|
215
|
+
|
216
|
+
# Example output: "v1stgxr8z5jd"
|
217
|
+
```
|
218
|
+
|
219
|
+
**Use cases:**
|
220
|
+
|
221
|
+
- Usernames
|
222
|
+
- Subdomains
|
223
|
+
- File names
|
224
|
+
- Consistent formatting
|
225
|
+
|
226
|
+
### No Confusing Characters
|
227
|
+
|
228
|
+
Generate IDs without characters that can be easily confused.
|
229
|
+
|
230
|
+
```ruby
|
231
|
+
class User < ApplicationRecord
|
232
|
+
include OpaqueId::Model
|
233
|
+
|
234
|
+
# Exclude confusing characters: 0, O, l, I, 1
|
235
|
+
self.opaque_id_alphabet = "ABCDEFGHJKLMNPQRSTUVWXYZabcdefghijkmnopqrstuvwxyz23456789"
|
236
|
+
self.opaque_id_length = 15
|
237
|
+
end
|
238
|
+
|
239
|
+
# Example output: "V2StGXR8Z5jdHi6B"
|
240
|
+
```
|
241
|
+
|
242
|
+
**Use cases:**
|
243
|
+
|
244
|
+
- Human-readable IDs
|
245
|
+
- Voice communication
|
246
|
+
- Hand-written transcription
|
247
|
+
- Accessibility
|
248
|
+
|
249
|
+
### Specialized Characters
|
250
|
+
|
251
|
+
Generate IDs with specific character sets for unique requirements.
|
252
|
+
|
253
|
+
```ruby
|
254
|
+
class Game < ApplicationRecord
|
255
|
+
include OpaqueId::Model
|
256
|
+
|
257
|
+
# Game-friendly characters (no vowels to avoid words)
|
258
|
+
self.opaque_id_alphabet = "BCDFGHJKLMNPQRSTVWXYZbcdfghjklmnpqrstvwxyz23456789"
|
259
|
+
self.opaque_id_length = 8
|
260
|
+
end
|
261
|
+
|
262
|
+
# Example output: "B2StGXR8"
|
263
|
+
```
|
264
|
+
|
265
|
+
**Use cases:**
|
266
|
+
|
267
|
+
- Game codes
|
268
|
+
- Room identifiers
|
269
|
+
- Tournament codes
|
270
|
+
- Content filtering
|
271
|
+
|
272
|
+
## Alphabet Selection Guide
|
273
|
+
|
274
|
+
### Choose by Use Case
|
275
|
+
|
276
|
+
#### Public URLs
|
277
|
+
|
278
|
+
```ruby
|
279
|
+
# URL-safe, human-readable
|
280
|
+
self.opaque_id_alphabet = OpaqueId::ALPHANUMERIC_ALPHABET
|
281
|
+
```
|
282
|
+
|
283
|
+
#### High Performance
|
284
|
+
|
285
|
+
```ruby
|
286
|
+
# Fastest generation
|
287
|
+
self.opaque_id_alphabet = OpaqueId::STANDARD_ALPHABET
|
288
|
+
```
|
289
|
+
|
290
|
+
#### Human Readable
|
291
|
+
|
292
|
+
```ruby
|
293
|
+
# No confusing characters
|
294
|
+
self.opaque_id_alphabet = "ABCDEFGHJKLMNPQRSTUVWXYZabcdefghijkmnopqrstuvwxyz23456789"
|
295
|
+
```
|
296
|
+
|
297
|
+
#### Maximum Security
|
298
|
+
|
299
|
+
```ruby
|
300
|
+
# High entropy, many characters
|
301
|
+
self.opaque_id_alphabet = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789!@#$%^&*"
|
302
|
+
```
|
303
|
+
|
304
|
+
#### Numeric Only
|
305
|
+
|
306
|
+
```ruby
|
307
|
+
# Numbers only
|
308
|
+
self.opaque_id_alphabet = "0123456789"
|
309
|
+
```
|
310
|
+
|
311
|
+
### Choose by Length
|
312
|
+
|
313
|
+
#### Short IDs (8-12 characters)
|
314
|
+
|
315
|
+
```ruby
|
316
|
+
# Use larger alphabets for shorter IDs
|
317
|
+
self.opaque_id_alphabet = OpaqueId::STANDARD_ALPHABET
|
318
|
+
self.opaque_id_length = 8
|
319
|
+
```
|
320
|
+
|
321
|
+
#### Medium IDs (15-21 characters)
|
322
|
+
|
323
|
+
```ruby
|
324
|
+
# Standard alphabets work well
|
325
|
+
self.opaque_id_alphabet = OpaqueId::ALPHANUMERIC_ALPHABET
|
326
|
+
self.opaque_id_length = 21
|
327
|
+
```
|
328
|
+
|
329
|
+
#### Long IDs (32+ characters)
|
330
|
+
|
331
|
+
```ruby
|
332
|
+
# Any alphabet works, consider performance
|
333
|
+
self.opaque_id_alphabet = OpaqueId::STANDARD_ALPHABET
|
334
|
+
self.opaque_id_length = 32
|
335
|
+
```
|
336
|
+
|
337
|
+
## Performance Considerations
|
338
|
+
|
339
|
+
### Alphabet Size Impact
|
340
|
+
|
341
|
+
Larger alphabets generally provide better performance due to optimized algorithms:
|
342
|
+
|
343
|
+
```ruby
|
344
|
+
# 64 characters - fastest (optimized path)
|
345
|
+
self.opaque_id_alphabet = OpaqueId::STANDARD_ALPHABET
|
346
|
+
|
347
|
+
# 62 characters - good performance
|
348
|
+
self.opaque_id_alphabet = OpaqueId::ALPHANUMERIC_ALPHABET
|
349
|
+
|
350
|
+
# 16 characters - slower (rejection sampling)
|
351
|
+
self.opaque_id_alphabet = "0123456789abcdef"
|
352
|
+
|
353
|
+
# 10 characters - slowest (rejection sampling)
|
354
|
+
self.opaque_id_alphabet = "0123456789"
|
355
|
+
```
|
356
|
+
|
357
|
+
### Character Set Optimization
|
358
|
+
|
359
|
+
```ruby
|
360
|
+
# Optimized for 64 characters
|
361
|
+
self.opaque_id_alphabet = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789-_"
|
362
|
+
|
363
|
+
# Good performance with 62 characters
|
364
|
+
self.opaque_id_alphabet = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789"
|
365
|
+
|
366
|
+
# Slower with smaller sets
|
367
|
+
self.opaque_id_alphabet = "ABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789"
|
368
|
+
```
|
369
|
+
|
370
|
+
## Security Considerations
|
371
|
+
|
372
|
+
### Entropy and Security
|
373
|
+
|
374
|
+
Larger alphabets provide more entropy per character:
|
375
|
+
|
376
|
+
```ruby
|
377
|
+
# High entropy (64 characters)
|
378
|
+
self.opaque_id_alphabet = OpaqueId::STANDARD_ALPHABET
|
379
|
+
self.opaque_id_length = 21
|
380
|
+
# Entropy: 21 * log2(64) = 126 bits
|
381
|
+
|
382
|
+
# Medium entropy (62 characters)
|
383
|
+
self.opaque_id_alphabet = OpaqueId::ALPHANUMERIC_ALPHABET
|
384
|
+
self.opaque_id_length = 21
|
385
|
+
# Entropy: 21 * log2(62) = 125 bits
|
386
|
+
|
387
|
+
# Lower entropy (16 characters)
|
388
|
+
self.opaque_id_alphabet = "0123456789abcdef"
|
389
|
+
self.opaque_id_length = 21
|
390
|
+
# Entropy: 21 * log2(16) = 84 bits
|
391
|
+
```
|
392
|
+
|
393
|
+
### Character Predictability
|
394
|
+
|
395
|
+
Avoid predictable character patterns:
|
396
|
+
|
397
|
+
```ruby
|
398
|
+
# Good - random character distribution
|
399
|
+
self.opaque_id_alphabet = OpaqueId::STANDARD_ALPHABET
|
400
|
+
|
401
|
+
# Avoid - sequential patterns
|
402
|
+
self.opaque_id_alphabet = "ABCDEFGHIJKLMNOPQRSTUVWXYZ"
|
403
|
+
|
404
|
+
# Avoid - common patterns
|
405
|
+
self.opaque_id_alphabet = "0123456789"
|
406
|
+
```
|
407
|
+
|
408
|
+
## Best Practices
|
409
|
+
|
410
|
+
### 1. Choose Appropriate Alphabet Size
|
411
|
+
|
412
|
+
- **64 characters**: Best performance, good security
|
413
|
+
- **62 characters**: Good balance, URL-safe
|
414
|
+
- **32 characters**: Moderate performance, specific use cases
|
415
|
+
- **16 characters**: Slower, specific requirements
|
416
|
+
- **10 characters**: Slowest, numeric-only needs
|
417
|
+
|
418
|
+
### 2. Consider URL Safety
|
419
|
+
|
420
|
+
```ruby
|
421
|
+
# URL-safe characters
|
422
|
+
self.opaque_id_alphabet = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789-_"
|
423
|
+
|
424
|
+
# Avoid URL-unsafe characters
|
425
|
+
self.opaque_id_alphabet = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789!@#$%^&*"
|
426
|
+
```
|
427
|
+
|
428
|
+
### 3. Avoid Confusing Characters
|
429
|
+
|
430
|
+
```ruby
|
431
|
+
# Exclude confusing characters
|
432
|
+
self.opaque_id_alphabet = "ABCDEFGHJKLMNPQRSTUVWXYZabcdefghijkmnopqrstuvwxyz23456789"
|
433
|
+
|
434
|
+
# Or use purge_chars option
|
435
|
+
self.opaque_id_purge_chars = ['0', 'O', 'l', 'I', '1']
|
436
|
+
```
|
437
|
+
|
438
|
+
### 4. Test Your Alphabet
|
439
|
+
|
440
|
+
```ruby
|
441
|
+
# Test alphabet generation
|
442
|
+
class User < ApplicationRecord
|
443
|
+
include OpaqueId::Model
|
444
|
+
|
445
|
+
self.opaque_id_alphabet = "ABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789"
|
446
|
+
self.opaque_id_length = 10
|
447
|
+
end
|
448
|
+
|
449
|
+
# Generate test IDs
|
450
|
+
5.times { puts User.new.opaque_id }
|
451
|
+
# => "V1STGXR8Z5"
|
452
|
+
# => "K8JH2MN9PL"
|
453
|
+
# => "Q3RT7S1V4X"
|
454
|
+
# => "B6NF9C2M8Y"
|
455
|
+
# => "D4HG7K1P5W"
|
456
|
+
```
|
457
|
+
|
458
|
+
## Common Alphabet Patterns
|
459
|
+
|
460
|
+
### E-commerce
|
461
|
+
|
462
|
+
```ruby
|
463
|
+
# Order numbers - numeric
|
464
|
+
class Order < ApplicationRecord
|
465
|
+
include OpaqueId::Model
|
466
|
+
self.opaque_id_alphabet = "0123456789"
|
467
|
+
self.opaque_id_length = 8
|
468
|
+
end
|
469
|
+
|
470
|
+
# Product codes - alphanumeric
|
471
|
+
class Product < ApplicationRecord
|
472
|
+
include OpaqueId::Model
|
473
|
+
self.opaque_id_alphabet = OpaqueId::ALPHANUMERIC_ALPHABET
|
474
|
+
self.opaque_id_length = 12
|
475
|
+
end
|
476
|
+
```
|
477
|
+
|
478
|
+
### API Development
|
479
|
+
|
480
|
+
```ruby
|
481
|
+
# API keys - hexadecimal
|
482
|
+
class ApiKey < ApplicationRecord
|
483
|
+
include OpaqueId::Model
|
484
|
+
self.opaque_id_alphabet = "0123456789abcdef"
|
485
|
+
self.opaque_id_length = 32
|
486
|
+
end
|
487
|
+
|
488
|
+
# API tokens - standard
|
489
|
+
class ApiToken < ApplicationRecord
|
490
|
+
include OpaqueId::Model
|
491
|
+
self.opaque_id_alphabet = OpaqueId::STANDARD_ALPHABET
|
492
|
+
self.opaque_id_length = 24
|
493
|
+
end
|
494
|
+
```
|
495
|
+
|
496
|
+
### Content Management
|
497
|
+
|
498
|
+
```ruby
|
499
|
+
# Article slugs - URL-safe
|
500
|
+
class Article < ApplicationRecord
|
501
|
+
include OpaqueId::Model
|
502
|
+
self.opaque_id_alphabet = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789-_"
|
503
|
+
self.opaque_id_length = 8
|
504
|
+
end
|
505
|
+
|
506
|
+
# Comments - standard
|
507
|
+
class Comment < ApplicationRecord
|
508
|
+
include OpaqueId::Model
|
509
|
+
self.opaque_id_alphabet = OpaqueId::ALPHANUMERIC_ALPHABET
|
510
|
+
self.opaque_id_length = 15
|
511
|
+
end
|
512
|
+
```
|
513
|
+
|
514
|
+
## Next Steps
|
515
|
+
|
516
|
+
Now that you understand alphabet configuration:
|
517
|
+
|
518
|
+
1. **Explore [Configuration](configuration.md)** for complete configuration options
|
519
|
+
2. **Check out [Use Cases](use-cases.md)** for real-world alphabet usage
|
520
|
+
3. **Review [Performance](performance.md)** for alphabet optimization tips
|
521
|
+
4. **Read [API Reference](api-reference.md)** for complete alphabet documentation
|