Отримати хеш-значення можна лише за допомогою md5sum (без імені файлу)


176

Я використовую md5sum для створення хеш-значення для файлу. Але мені потрібно лише отримати значення хеша, а не ім'я файлу.

md5=`md5sum ${my_iso_file}`
echo ${md5}

3abb17b66815bc7946cefe727737d295 ./iso/somefile.iso

Як я можу "зняти" ім'я файлу і залишитися лише значенням?


27
Дуже дивно, що це не варіант для md5sum.
— Шрідхар Сарнобат

11
Домовились! Чому це не варіант? Чи може магістр GNU пролити трохи світла?
— rinogo

Чому вам потрібно мати прапор "тільки хеш", коли ви можете обрізати результат деяким регулярним виразом? (Я саркастичний)
— Magnetic_dud

Відповіді:


163

Ну інший спосіб :)

md5=`md5sum ${my_iso_file} | awk '{ print $1 }'`

7
Або md5=`md5sum < ${my_iso_file}` однак це все ще виводить "-" наприкінці. Але для порівнянь цього має бути достатньо.
— Крістоф Де Троєр

Неправильно він дає наступний вихід на Mac MD5 (/Users/hello.txt) = 24811012be8faa36c8f487bbaaadeb71і ваш код повертається MD5.
— альпер

Ви можете розпочати роботу -, додавши | awk '{print $1}'кінець свого коду => md5sum < ${my_iso_file} | awk '{print $1}'@ChristopheDeTroyer
— alper

191

Просте призначення масиву працює ... Зверніть увагу, що перший елемент bashмасиву може бути адресований просто індексом nameбез [0]індексу, тобто $md5містить лише 32 символи md5sum.

md5=($(md5sum file))
echo $md5
# 53c8fdfcbb60cf8e1a1ee90601cc8fe2

Дивовижно. Лише одне запитання, я знаю, що це позначено тегами bash, але чи можете ви сказати мені, чи масив є лише функцією bash або якимсь стандартним оболонки?
— jyz

перший рядок не працює в розділі do циклу для циклу ... як новобранець Баша, я ще не знаю, чому
— Енді

@Andy: Якщо ви спробуєте цей рядок коду (в терміналі або в скрипті): echo>file; for i in file; do md5=($(md5sum file)); echo $md5; done- Це повинно вивести68b329da9893e34099c7d8ad5cb9c940
— Peter.O

1
Як echo ($(echo -n foo | md5sum))це не працює? Помилки bash: syntax error near unexpected token $(echo -n foo | md5sum)'
— lkraav

2
@lkraav: Команда echo -n foo | md5sum виводить два слова оболонки до stdout : acbd18db4cc2f85cedef654fccc4a4d8і -( -вказує джерело як stdin ). - Ви повинні сказати Баш , щоб захопити ці слова в рядок, використовуючи Підстановку команд : $( command ). - (Дужки )створюють масив bash з 2 елементами. Однак ви повинні призначити цю конструкцію масиву ( … )імені змінної; отже, використовуючи md5 як ім'я масиву: md5=($(echo -n foo | md5sum)). Ви не призначили масив імені змінної
— Peter.O

57

Ви можете використовувати cutдля розділення рядка на пробіли та повернення лише першого такого поля:

md5=$(md5sum "$my_iso_file" | cut -d ' ' -f 1)

18
Абоcut -c 1-32
— Czarek Tomczak

7
@CzarekTomczak Щоправда, але просто використовуючи метод цієї відповіді, ви можете повторно використовувати його за допомогою різних алгоритмів хешування, просто змінивши саму команду. md5sum-> sha256sumне пам’ятаючи, яку кількість символів потрібно «вирізати».
— Девід Табернеро М.


14
md5="$(md5sum "${my_iso_file}")"
md5="${md5%% *}" # remove the first space and everything after it
echo "${md5}"

Приємно. Одна примітка - у першому рядку вам не потрібні цитати $()(хоча вони не приносять шкоди), але, безумовно, потрібні ${}.
— Роман Чепляка

1
@ Роман: Так, я, як правило, цитую будь-яке розширення (якщо немає причини цього не робити) - це простіше, ніж відслідковувати випадки, коли безпечно пропустити цитати. (Хоча в цьому випадку я залишив їх фактичним іменем файлу ... очікуйте на редагування.)
— Гордон Девіссон,

5

Односторонній:

set -- $(md5sum $file)
md5=$1

Інший спосіб:

md5=$(md5sum $file | while read sum file; do echo $sum; done)

Інший спосіб:

md5=$(set -- $(md5sum $file); echo $1)

(Не намагайтеся це робити із зворотними кліщами, якщо ви не дуже сміливі та дуже хороші з накидами.)

Перевага цих рішень перед іншими рішеннями полягає в тому, що вони лише викликають md5sumі оболонку, а не інші програми, такі якawk або sed. Чи це насправді має значення, то це окреме питання; вам, мабуть, буде важко помітити різницю.


4

Ще один спосіб:

md5sum filename |cut -f 1 -d " "

Вирізання розділить лінію на кожен пробіл і поверне лише перше поле.



2

Якщо вам потрібно роздрукувати його і не потрібен новий рядок, ви можете використовувати:

printf $(md5sum filename)


0

md5sumставить зворотну косу рису перед хешем, якщо в імені файлу є зворотна косою рисою. Перші 32 символи або що-небудь перед першим пробілом може бути не належним хешем. Це не відбудеться при використанні стандартного вводу (ім'я файлу буде просто -), тому відповідь pixelbeat спрацює, але багато інших потребуватимуть додавання чогось подібного | tail -c 32.


0

Що ж, у мене була та сама проблема сьогодні, але намагаюся отримати файл md5 хеш при виконанні findкоманди. Я отримав найбільш проголосоване запитання і вклав його у функцію, закликану md5запустити команду пошуку Місією для мене було обчислити хеш для всіх файлів у папці та вивести його як hash:filename.

md5() { md5sum $1 | awk '{ printf "%s",$1 }'; }
export -f md5
find -type f -exec bash -c 'md5 "$0"' {} \; -exec echo -n ':' \; -print

Отже, я отримав би фрагменти звідси, а також від find -exec функції оболонки?


0

Для повноти спосіб з sed використовуючи регулярний вираз і групу захоплення:

md5=$(md5sum "${my_iso_file}" | sed -r 's:\\*([^ ]*).*:\1:')

Регулярний вираз охоплює все в групі, поки не буде досягнуто пробілу. Для роботи групи захоплення вам потрібно захопити все в sed. (Докладніше про групи sed і caputer тут: https://stackoverflow.com/a/2778096/10926293 )
Як роздільник в sed я використовую колонки, оскільки вони не дійсні в файлових шляхах, і мені не потрібно уникати розрізаних в filepath.



Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.