2009-07-13 19 views
97

Tôi gặp sự cố thực sự dễ dàng được giải quyết với các hướng dẫn.Tạo các hướng dẫn trong Ruby

Cụ thể, đối với quy trình đặt lại mật khẩu, tôi muốn gửi mã thông báo Guid tới email của người dùng và yêu cầu họ đặt lại mật khẩu của họ bằng mã thông báo. Kể từ khi guids là duy nhất, điều này là khá an toàn và giúp tôi gửi email cho mọi người mật khẩu, đó là nguy hiểm.

Tôi nhận thấy có một Guid gem dành cho Ruby; nhưng nó trông khá cũ, và nó ghi công cụ vào hệ thống tập tin.

Có ai biết về bất kỳ loại đá quý nào khác có thể tạo số nhận dạng duy nhất toàn cầu không?

Tôi biết tôi chỉ có thể rơi trở lại:

(0..16).to_a.map{|a| rand(16).to_s(16)}.join 

Nhưng nó không thực sự có vẻ giống như một GUID thích hợp ...

+0

Sử dụng chuỗi ngẫu nhiên như vậy sẽ không hoàn toàn đúng; một số bit nhất định trong UUID chỉ định biến thể và phiên bản. Đối với UUID ngẫu nhiên, bạn có thể muốn biến thể 2 (RFC 4122) và phiên bản 4, trong trường hợp này 6 bit nhất định phải được đặt thành giá trị đúng. – jtpereyda

+1

Có @dafrazzman là đúng. Ngẫu nhiên ghép nối với nhau một cái gì đó mà "giống như một UUID" không đảm bảo tính duy nhất. Trong khi không có UUID nào * thật sự * được đảm bảo, việc xây dựng một con số với số ngẫu nhiên là FAR dễ bị va chạm và không thể xứng đáng với nhãn "UUID". Chắc chắn đi với SecureRandom.uuid! – dooleyo

Trả lời

207

Kể từ phiên bản Ruby 1.9, thế hệ uuid được tích hợp sẵn. Sử dụng chức năng SecureRandom.uuid.

Ví dụ:

require 'securerandom' 
SecureRandom.uuid # => "96b0a57c-d9ae-453f-b56f-3b154eb10cda" 
+5

SecureRandom.uuid tạo ra một UUID ngẫu nhiên, vì vậy nó không được đảm bảo là duy nhất. Nếu bạn chỉ muốn một chuỗi ngẫu nhiên có lẽ là duy nhất thì sẽ không sao nếu sử dụng nó. Tuy nhiên, nếu bạn muốn một cái gì đó được đảm bảo là duy nhất, bạn sẽ cần phải sử dụng một cái gì đó bao gồm địa chỉ MAC, dấu thời gian, và vân vân. –

+20

Để tiết kiệm cho bạn một chút tra cứu, bạn cần phải yêu cầu 'securerandom' –

+8

Nó không được đảm bảo là duy nhất, nhưng với hầu hết các mục đích thực tế, nó là an toàn để cho rằng nó là duy nhất. Xem: http://stackoverflow.com/questions/2977593/is-it-safe-to-assume-a-guid-will-always-be-unique –

20

Bạn có nhìn vào UUIDTools?

UUIDTools được thiết kế để trở thành một thư viện đơn giản để tạo bất kỳ loại UUID nào (hoặc GUID nếu bạn muốn gọi chúng). Nó phù hợp với RFC 4122 bất cứ khi nào có thể.

+0

nope không nhận thấy điều đó. Dường như nó giải quyết được vấn đề của tôi –

+0

Rất tuyệt - Tôi hy vọng nó có thể lừa được :) –

31

How to create small, unique tokens in Ruby

>> require 'digest' 
=> [] 
>> Digest::SHA1.hexdigest("some-random-string")[8..16] 
=> "2ebe5597f" 

>> SecureRandom.base64(8).gsub("/","_").gsub(/=+$/,"") 
=> "AEWQyovNFo0" 

>> rand(36**8).to_s(36) 
=> "uur0cj2h" 
+2

Có rất nhiều giải pháp thực sự tuyệt vời trên trang này. – Abel

+4

Trong trường hợp ai đó muốn tìm kiếm điều này. [Máy Wayback] (http://web.archive.org/web/20120925034700/http://blog.logeek.fr/2009/7/2/creating-small-unique-tokens-in-ruby) – engineerDave

14

Google mang lại thư viện của Ruby sau:

http://raa.ruby-lang.org/project/ruby-guid/

Ngoài ra, qua tại http://www.ruby-forum.com/topic/99262 họ nói rằng bạn có thể cài đặt một viên ngọc (thực hiện gem uuid trên dòng lệnh để cài đặt nó) và sau đó làm

gem 'uuid' 
puts UUID.new 

trong mã của bạn để xem UUID mới.

(Gợi ý: Tôi google để tìm ruby ​​guid)

+0

thx I thấy điều đó nhưng nó siêu cũ, chỉ cần tìm một cái gì đó hoạt động, giống như một viên đá quý gần đây? –

+2

Không có gì sai với một thư viện cũ. –

+0

Làm thế nào về đá quý uuid tôi thêm vào câu trả lời của tôi? Hay là người bạn đang đề cập đến? –

34

Chúng tôi sử dụng UUIDTools và không có vấn đề với nó.

+2

'uuidtools' hoạt động, ngay cả khi hệ thống không có địa chỉ MAC. 'uuid' không thành công trong trường hợp này. – grefab

+3

Không giống như đá quý uuid, uuidtools không giữ tập tin trạng thái. Các vấn đề về quyền với tệp trạng thái làm cho đá quý uuid hơi khó xử khi sử dụng với nhiều người dùng. –

+0

Dường như công cụ UUID không được duy trì nữa. Không có bất kỳ cam kết nào với repo github trong hơn 2 năm – dotnetguy

1

Trong khi lập trình muộn vào ban đêm tôi đã đưa ra các giải pháp sau (dựa trên Simone) để tạo ra một GUID duy nhất trong Rails. Tôi không tự hào về nó nhưng nó hoạt động khá tốt.

while Order.find_by_guid(guid = rand(36**8).to_s(36).upcase).present?; end 
+1

Tôi hy vọng bạn nhớ chỉ mục cột guid của bạn rằng đêm – nurettin

1

Để tạo thích hợp, mysql, varchar 32 GUID

SecureRandom.uuid.gsub('-','').upcase 
0

Khi tôi sử dụng đá quý uuid đề nghị trong câu hỏi này, không ai có thể tạo ra UUID độc đáo và ngẫu nhiên. Câu trả lời của tôi là một công việc xung quanh, nếu chúng ta có đá quý sau để đáp ứng yêu cầu, bạn nên sử dụng gem trong Ruby.

Tôi thử đá quý uuid được đề xuất nhất trong câu hỏi này, nhưng không ai làm tôi hài lòng, chúng tôi cần uuid độc đáo và ngẫu nhiên. Tôi trực tiếp chạy lệnh hệ thống uuidgen trong ruby, và tôi thích kết quả, và chia sẻ ở đây.

puts `uuidgen` 
8adea17d-b918-43e0-b82f-f81b3029f688 
puts `uuidgen` 
6a4adcce-8f64-41eb-bd7e-e65ee6d11231 
puts `uuidgen` 
51d5348b-8fc3-4c44-a6f7-9a8588d7f08a 
puts `uuidgen` 
332a0fa3-7b07-41e1-9fc8-ef804a377e4e 

nếu so sánh với uuid đá quý, bạn sẽ biết sự khác biệt.

irb(main):003:0> uuid.generate 
=> "40cdf890-ebf5-0132-2250-20c9d088be77" 
irb(main):004:0> uuid.generate 
=> "4161ac40-ebf5-0132-2250-20c9d088be77" 

Môi trường kiểm tra là môi trường Linux và Mac OS.

+1

một 'puts \' ... \ '' về cơ bản đang thực hiện một cuộc gọi hệ thống tới 'uuidgen (3)' không thành công trên bất kỳ nền tảng nào khác ngoài Linux, bổ sung số lượng cực đoan của thời gian thực hiện và nói chung thực sự là thực hành mã hóa trực quan. Tại sao bạn lại chọn phương thức như vậy? –

+1

@DwightSpencer Tôi nghĩ rằng chúng tôi đang ở trong khu vực khác nhau với mục đích khác nhau. Những gì bạn quan tâm là không có trong mối quan tâm của tôi ở tất cả, chẳng hạn như thời gian thực hiện, phạm vi rộng của các hệ điều hành, di chuyển mã. Tôi quan tâm mã có thể làm việc trong Mac OS hoặc Linux dòng chính và có được kết quả đúng tôi cần. Của couse, nếu bạn có thể làm việc ra một cách trong Ruby và nhận được kết quả tương tự như lệnh uuidgen, tôi rất vui khi sử dụng nó. Nhưng cho đến bây giờ, tôi không tìm thấy gì cả. – BMW

+0

Cả hai @J_ và @ simone-carletti đã chỉ ra một cách tốt hơn trên bài đăng này. Tôi cho một người sẽ đề nghị 'SecureRandom' vì nó có chức năng tương tự trong cùng một phương thức với' uuidgen' nhưng không giống như việc 'sử dụng'/dev/random ''SecureRandom' sử dụng thư viện openssl trước tiên rồi thả xuống dev/urandom sau đó cuối cùng/dev/ngẫu nhiên trong nỗ lực để làm không chặn ngẫu nhiên thế hệ. –

2

cập nhật nhỏ để Simone Carletti câu trả lời:.

SecureRandom.base64 (8) .gsub ("/", "_") gsub (/ = + $/"")

=> "AEWQyovNFo0"

có thể được thay thế bằng:

SecureRandom.urlsafe_base64 (8)

Các vấn đề liên quan