Декодирование Base32

Вы правы, что spring-data-r2dbc не является ORM. Он не отображает отношения в вашей базе данных. Что он может сделать, так это сопоставить строки вашей базы данных с объектами. Следующий фрагмент кода сопоставляется со строкой базы данных ниже:

Пример класса в Kotlin:

@Table("song")
class SongRow(
    @Id val id: Long, 
    val name: String, 
    val artist: Long
)

Строка:

create table song(
    id integer identity primary key,
    artist integer references artist(id),
    name varchar(100) NOT NULL,
);

Для способа автоматического получения столбцов в соответствии с вашей моделью см .: https://docs.spring.io/spring-data/r2dbc/docs/1.0.0.M1/reference/html/#mapping-usage

В ссылке выше также указано, что вы можете использовать @Column.

Что касается одного из ваших вопросов:

Какие варианты существуют или планируются для поддержки ORM в реактивных приложениях? Понятия не имею

blockquote>

Что касается:

присоединяется при использовании spring-data-r2dbc

blockquote>

Используя аннотацию @Query, вы может выполнять соединения. Если вы хотите отобразить данные, полученные с помощью объединений, вам лучше использовать DatabseClient (см. https://docs.spring.io/spring-data/r2dbc/docs/1.0.0.M1 /reference/html/#r2dbc.datbaseclient)

32
задан phuclv 9 April 2018 в 11:10
поделиться

3 ответа

Проверьте этот FromBase32String, реализация для.NET нашла здесь .

<час>

Редактирование: вышеупомянутая ссылка была битой; можно найти заархивированную копию в archive.org

фактическое чтение кода:

using System;
using System.Text;

public sealed class Base32 {

      // the valid chars for the encoding
      private static string ValidChars = "QAZ2WSX3" + "EDC4RFV5" + "TGB6YHN7" + "UJM8K9LP";

      /// <summary>
      /// Converts an array of bytes to a Base32-k string.
      /// </summary>
      public static string ToBase32String(byte[] bytes) {
            StringBuilder sb = new StringBuilder();         // holds the base32 chars
            byte index;
            int hi = 5;
            int currentByte = 0;

            while (currentByte < bytes.Length) {
                  // do we need to use the next byte?
                  if (hi > 8) {
                        // get the last piece from the current byte, shift it to the right
                        // and increment the byte counter
                        index = (byte)(bytes[currentByte++] >> (hi - 5));
                        if (currentByte != bytes.Length) {
                              // if we are not at the end, get the first piece from
                              // the next byte, clear it and shift it to the left
                              index = (byte)(((byte)(bytes[currentByte] << (16 - hi)) >> 3) | index);
                        }

                        hi -= 3;
                  } else if(hi == 8) { 
                        index = (byte)(bytes[currentByte++] >> 3);
                        hi -= 3; 
                  } else {

                        // simply get the stuff from the current byte
                        index = (byte)((byte)(bytes[currentByte] << (8 - hi)) >> 3);
                        hi += 5;
                  }

                  sb.Append(ValidChars[index]);
            }

            return sb.ToString();
      }


      /// <summary>
      /// Converts a Base32-k string into an array of bytes.
      /// </summary>
      /// <exception cref="System.ArgumentException">
      /// Input string <paramref name="s">s</paramref> contains invalid Base32-k characters.
      /// </exception>
      public static byte[] FromBase32String(string str) {
            int numBytes = str.Length * 5 / 8;
            byte[] bytes = new Byte[numBytes];

            // all UPPERCASE chars
            str = str.ToUpper();

            int bit_buffer;
            int currentCharIndex;
            int bits_in_buffer;

            if (str.Length < 3) {
                  bytes[0] = (byte)(ValidChars.IndexOf(str[0]) | ValidChars.IndexOf(str[1]) << 5);
                  return bytes;
            }

            bit_buffer = (ValidChars.IndexOf(str[0]) | ValidChars.IndexOf(str[1]) << 5);
            bits_in_buffer = 10;
            currentCharIndex = 2;
            for (int i = 0; i < bytes.Length; i++) {
                  bytes[i] = (byte)bit_buffer;
                  bit_buffer >>= 8;
                  bits_in_buffer -= 8;
                  while (bits_in_buffer < 8 && currentCharIndex < str.Length) {
                        bit_buffer |= ValidChars.IndexOf(str[currentCharIndex++]) << bits_in_buffer;
                        bits_in_buffer += 5;
                  }
            }

            return bytes;
      }
}
13
ответ дан 27 November 2019 в 19:43
поделиться

Вот мое быстро кратко записанное решение. Это только работает над строками, которые являются кратными 8 base32 символам. Действительно работает, все же.

public class Base32
{
  /// <summary>
  /// Decode a Base32 string
  /// This will only work on a multiple of 40 bits (5 bytes)
  /// http://www.garykessler.net/library/base64.html
  /// </summary>
  public static byte[] Decode(string Base32String)
  {
    // Ignore hyphens
    string str = Base32String.Replace("-", "");

    // Convert it to bits
    List<byte> bits = new List<byte>();
    foreach (char c in str)
    {
      int i = CharToValue(c);
      bits.Add((byte)((i & 16) > 0 ? 1 : 0));
      bits.Add((byte)((i & 8) > 0 ? 1 : 0));
      bits.Add((byte)((i & 4) > 0 ? 1 : 0));
      bits.Add((byte)((i & 2) > 0 ? 1 : 0));
      bits.Add((byte)((i & 1) > 0 ? 1 : 0));
    }

    // Convert bits into bytes
    List<byte> bytes = new List<byte>();
    for (int i = 0; i < bits.Count; i += 8)
    {
      bytes.Add((byte)(
        (bits[i + 0] << 7) +
        (bits[i + 1] << 6) +
        (bits[i + 2] << 5) +
        (bits[i + 3] << 4) +
        (bits[i + 4] << 3) +
        (bits[i + 5] << 2) +
        (bits[i + 6] << 1) +
        (bits[i + 7] << 0)));
    }

    return bytes.ToArray();
  }

  static int CharToValue(char c)
  {
    char cl = char.ToLower(c);
    if (cl == 'a') return 0;
    if (cl == 'b') return 1;
    if (cl == 'c') return 2;
    if (cl == 'd') return 3;
    if (cl == 'e') return 4;
    if (cl == 'f') return 5;
    if (cl == 'g') return 6;
    if (cl == 'h') return 7;
    if (cl == 'i') return 8;
    if (cl == 'j') return 9;
    if (cl == 'k') return 10;
    if (cl == 'l') return 11;
    if (cl == 'm') return 12;
    if (cl == 'n') return 13;
    if (cl == 'o') return 14;
    if (cl == 'p') return 15;
    if (cl == 'q') return 16;
    if (cl == 'r') return 17;
    if (cl == 's') return 18;
    if (cl == 't') return 19;
    if (cl == 'u') return 20;
    if (cl == 'v') return 21;
    if (cl == 'w') return 22;
    if (cl == 'x') return 23;
    if (cl == 'y') return 24;
    if (cl == 'z') return 25;
    if (cl == '2') return 26;
    if (cl == '3') return 27;
    if (cl == '4') return 28;
    if (cl == '5') return 29;
    if (cl == '6') return 30;
    if (cl == '7') return 31;
    throw new Exception("Not a base32 string");
  }
}
1
ответ дан 27 November 2019 в 19:43
поделиться

Я написал несколько гибких реализаций на основе стандартов различных методов кодирования/декодирования Base32 и Base64. В частности: base64url (согласно rfc4648) и его эквивалент base32.

По умолчанию класс Base32Url кодирует только символы от A до Z и от 2 до 7. Не используются дефисы, подчеркивания, плюсы, косые черты или знаки равенства, что делает его пригодным для использования в качестве маркера URL почти при любых обстоятельствах. Base32Url также поддерживает пользовательские алфавиты, чувствительность/нечувствительность к регистру, вставку/невставку и т.д.

Это размещено на code project.

5
ответ дан 27 November 2019 в 19:43
поделиться
Другие вопросы по тегам:

Похожие вопросы: