Крипто в рубине и буквенно-цифровой - PullRequest
0 голосов
/ 07 июня 2009

Я работаю над проектом, который включает URL-адрес «пересылки» (например, bit.ly или tinyurl.com, но нам не нужно, чтобы он был коротким).

Для этого мне нужно «сгенерировать» буквенно-цифровые строки (я явно хочу буквенно-цифровые) для сопоставления с каждым URL. Один из вариантов будет генерировать случайную строку и хранить ее где-нибудь. Тем не менее, я бы хотел избежать использования базы данных, поскольку мы не используем ее в нашем приложении. Я хочу на самом деле «закодировать» URL, чтобы он мог быть декодирован позже.

Какие-нибудь советы, как это сделать?

Ответы [ 5 ]

4 голосов
/ 07 июня 2009

Я думаю, что на самом деле нашел лучшее решение (по крайней мере, более подходящее и простое для реализации в моем случае)

Это как-то хак, который состоит из распаковки строки с параметром H *. Вот пример кода:

url =  "/662341/kripto-v-rubine-i-bukvenno-tsifrovoi"
unpacked = url.unpack("H*")  # => 687474703a2f2f737461636b6f766572666c6f772e636f6d2f7175657374696f6e732f3936303635382f63727970746f2d696e2d727562792d616e642d616c7068616e756d65726963
unpacked.pack("H*")  # => /662341/kripto-v-rubine-i-bukvenno-tsifrovoi

Я не буду отмечать это как ответ (даже не уверен, что смогу ...), но я хотел бы сообщить читателям, что это действительно помогло мне;)

2 голосов
/ 07 июня 2009

Не может быть сделано. Произвольный URL-адрес содержит много символов - скажем, 100. Сокращенный URL-адрес может содержать, возможно, 5. Вы не можете использовать 5 символов для восстановления 100 без какой-либо таблицы поиска; просто недостаточно информации для этого.

РЕДАКТИРОВАТЬ 1: Что ж, если вам на самом деле не нужен URL сокращатель (тогда зачем вы это написали?), Существует множество вариантов. Я бы выбрал простую кодировку Base64, возможно, после прохода через zlib или другой компрессор (который может сделать URL длиннее; вам придется измерить, помогает это или нет).

РЕДАКТИРОВАТЬ 2: Стандартный Base64 использует три не алфавитно-цифровые символы: +, / и -. Если это неприемлемо, у вас есть несколько вариантов:

  1. Модифицированный Base64. Википедия предлагает «модифицированный Base64 для URL», который отбрасывает все = и заменяет + и / на - и _ соответственно. Но они все еще не алфавитно-цифровые, что вам не поможет.

  2. Некоторые специальные схемы, такие как Base32 или Base36. Это действительно легко реализовать, если вы знаете, как делается Base64 (см. Ссылку выше). (Правка 3: я думаю, что Base32 на самом деле стандартизирован . Похоже, RFC 4648 Base32 с заполнением 8 вместо = будет работать для вас просто отлично).

  3. Какой-то полустандартный подход. Есть много возможностей. К сожалению, большинство из них полагаются на пару специальных не буквенно-цифровых символов, просто потому, что, используя всего один или два символа, вы можете получить гораздо более высокую производительность. Взгляните на двоично-текстовую кодировку для лучшего обзора, чем я могу дать.

1 голос
/ 23 февраля 2011

Большинство людей, которые попадают на эту страницу, вероятно, ищут способ генерировать строки в стиле TinyURL с использованием Ruby. (Вот как я это нашел.)

Хорошая новость в том, что это очень просто.

# timestamp
>> DateTime.now.hash.abs.to_s(36)
=> "5ynfka" 

# invite code
>> "joe@momma.org".hash.to_s(36)
=> "emhs98"

На основании http://blog.internautdesign.com/2007/11/2/base-conversion-and-tiny-url-type-hashes-in-ruby

0 голосов
/ 08 июня 2009

Пока вы не возражаете против уродливых URL, вы можете сделать быстрый с base64 и url escape:

require 'base64'
require 'cgi'
require 'uri'

def encode_url(url)
  CGI.escape(Base64.encode64(url))
end

И обратно:

def decode_url(encoded_url)
  Base64.decode64(CGI.unescape(encoded_url))
end

Большие уродливые URL, но это сделало бы работу:

>> u = encode_url("http://railsruby.blogspot.com/2006/07/url-escape-and-url-unescape.html")
=> "aHR0cDovL3JhaWxzcnVieS5ibG9nc3BvdC5jb20vMjAwNi8wNy91cmwtZXNj%0AYXBlLWFuZC11cmwtdW5lc2NhcGUuaHRtbA%3D%3D%0A"
>> decode_url u
=> "http://railsruby.blogspot.com/2006/07/url-escape-and-url-unescape.html"
0 голосов
/ 07 июня 2009

Простой способ сделать это - перечислить все символы, разрешенные в URL-адресе, которые не являются буквенно-цифровыми - я быстро выбрал быстрый поиск в Интернете: $ -_. +! * '(); / ?: @ = & - и просто как-то их кодировать. В моем списке 17 символов, и самый простой способ их кодирования без потери разборчивости, о котором я могу подумать, - это выбрать один буквенно-цифровой символ, скажем s, в качестве кода смены:

$ ⇒ s0    - ⇒ s1    _ ⇒ s2    . ⇒ s3    + ⇒ s4    ! ⇒ s5
* ⇒ s6    ' ⇒ s7    ( ⇒ s8    ) ⇒ s9    ; ⇒ sa    / ⇒ sb
? ⇒ sc    : ⇒ sd    @ ⇒ se    = ⇒ sf    & ⇒ sg    s ⇒ ss

Другой подход заключается в преобразовании исходного URL-адреса в битовый поток, предпочтительно с некоторым алгоритмом сжатия, поскольку вы уже утратили разборчивость, и затем назначением буквенно-цифрового символа для каждой возможной 6-битной последовательности. Обратите внимание, что в результате остаются 4 буквенно-цифровых символа, которые вы никогда не используете - вы можете вернуть их, если действительно заботитесь о длине, но вряд ли это стоит осложнений.

Я проигнорирую слово "крипто" в теме, так как вы, кажется, не заинтересованы в том, чтобы усложнить обнаружение схемы.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...