Попытка передать случайную строку в SHA в Haskell - PullRequest
1 голос
/ 15 апреля 2019

Я пытаюсь передать случайную строку (которая оказывается числом) "4176730.5" в SHA в Haskell, чтобы получить большую случайную строку, например "2d711642b726b04401627ca9fbac32f5c8530fb1903cc4db02258717921a4881".

У меня есть этот код для генерации случайного числа и преобразования его в строку

  num <- randomIO :: IO Float

  let x = C.pack (show (num*10000000))

  print x

но когда я передаю его в SHA с

  let a = sha256 x

Я получаю ошибку

Couldn't match expected type ‘Data.ByteString.Lazy.Internal.ByteString’
            with actual type ‘C.ByteString’

Я пытался привести свое число к C.ByteString, но я думаю, что согласно компилятору Haskell есть два типа Bytestring.

Полный код:

import Data.Digest.Pure.SHA
import System.Random
import qualified Data.ByteString.Char8 as C

main :: IO ()

main = do
  num <- randomIO :: IO Float

  let x = C.pack (show (num*10000000))

  print x

  let a = sha256 x

      b = hmacSha256 "key" "some test message"
  mapM_ print [showDigest a, showDigest b]

Видя, как, по-видимому, существует два типа Bytestring, и я приведу к неправильному, как правильно привести свою случайную строку?

В дополнение к ответу @ Cubic ниже, если я заменю импортировать квалифицированный Data.ByteString.Char8 как C с

import qualified Data.ByteString.Lazy as C

Я просто получаю эти ошибки

Couldn't match type ‘Char’ with ‘GHC.Word.Word8’
Expected type: [GHC.Word.Word8]
  Actual type: String

и

Couldn't match expected type ‘C.ByteString’
            with actual type ‘[Char]’

Ответы [ 3 ]

2 голосов
/ 15 апреля 2019

Проблема в том, что ByteString - это последовательность байтов, а String - это последовательность символов.Есть много способов превратить символы в байты, поэтому вам нужно указать, какую кодировку вы хотите.Скорее всего, вам нужна кодировка ASCII или UTF8.Если это так, вы можете использовать это решение ниже, которое при необходимости преобразует строки в «байты UTF8».

import Data.Digest.Pure.SHA
import System.Random
import qualified Data.ByteString.Lazy as C
import qualified Data.ByteString.Lazy.UTF8 as U

main :: IO ()

main = do
  num <- randomIO :: IO Float

  let x = U.fromString (show (num*10000000))

  print x

  let a = sha256 x

      b = hmacSha256 (U.fromString "key") (U.fromString "some test message")
  mapM_ print [showDigest a, showDigest b]
0 голосов
/ 15 апреля 2019

Просто используйте ленивые строки байтов, как упомянуто @leftaroundabout. Ваша попытка не сработала, потому что вы хотите упаковать из Strings, поэтому вам нужно импортировать модуль .Char8, чтобы добиться этого:

import Data.ByteString.Lazy.Char8 as C
0 голосов
/ 15 апреля 2019

Вам нужно Data.ByteString.Lazy, а не Data.ByteString.Char8.

В общем, вы почти никогда не хотите Data.ByteString.Char8.

...