Every order in my online store has a user-facing order number. I'm wondering the best way to generate them. Criteria include:
Right now I'm using the following method (no checksum):
def generate_number possible_values = 'abfhijlqrstuxy'.upcase.split('') | '123456789'.split('') record = true while record random = Array.new(5){possible_values[rand(possible_values.size)]}.join record = Order.find(:first, :conditions => ["number = ?", random]) end self.number = random end
Shopify order numbers are generated using a sequence. When you first create a brand new store that number starts as 1001. Meaning the first order you create will be created with an order number of #1001. The next order that is created will be #1002 and so on.
pre-generate the entire set and pick from them randomly (a few hundred GB of database) Use lexicographical "next_permutation" starting from a particular seed number. MD5 or SHA-1 hash of the date, user-id, etc parameters, truncated to 14 digits.
As a customer I would be happy with:
year-month-day/short_uid
for example:
2009-07-27/KT1E
It gives room for about 33^4 ~ 1mln orders a day.
Here is an implementation for a system I proposed in an earlier question:
MAGIC = []; 29.downto(0) {|i| MAGIC << 839712541[i]} def convert(num) order = 0 0.upto(MAGIC.length - 1) {|i| order = order << 1 | (num[i] ^ MAGIC[i]) } order end
It's just a cheap hash function, but it makes it difficult for an average user to determine how many orders have been processed, or a number for another order. It won't run out of space until you've done 230 orders, which you won't hit any time soon.
Here are the results of convert(x)
for 1 through 10:
1: 302841629 2: 571277085 3: 34406173 4: 973930269 5: 437059357 6: 705494813 7: 168623901 8: 906821405 9: 369950493 10: 638385949
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With