-
-
Save PushPressureTM/7f09a154ef457ef1b04f1137a9054f30 to your computer and use it in GitHub Desktop.
Download all files from a Slack workspace export folder - Skip Cancelled Jobs (cancel(led) in name of slack channel) - Ensure File Type Support
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#!/bin/bash | |
# | |
# This script will browse a Slack export folder and download all files in a new /export folder | |
# | |
# HOW TO: | |
# 1. As a Workspace admin, download an export of your Slack history (https://www.slack.com/services/export) | |
# 2. Make sure you have jq installed (https://stedolan.github.io/jq/) | |
# 3. Place this file at the root of your Slack export folder, next to channels.json | |
# 4. Run `bash slack-files-downloader.sh` in your terminal | |
# | |
# OPTIONS | |
# -o Overwrite files if they already exist in destination folder, otherwise skip them. | |
# -s Do not show message when a file is skipped | |
# -l Store links to external files into an html file at expected path | |
# -v Verbose logging of file paths | |
loglevel=0 | |
while getopts "oslv" flag | |
do | |
case $flag in | |
o) overwrite=true;; | |
s) silent=true;; | |
l) link_external=true;; | |
v) loglevel=$((loglevel+1));; | |
esac | |
done | |
printf "\nSelect one specific file type to download or leave empty for any (e.g. mp3, binary, jpg, png):\n" | |
read usertype | |
printf "\nSelect a channel to look into or leave empty for all channels:\n" | |
read userchannel | |
printf "\n~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~\nExporting channels\n~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~\n" | |
if [[ -z $userchannel ]] | |
then | |
export_channels=$(cat channels.json | jq -rc '.[].name') | |
else | |
export_channels=$userchannel | |
fi | |
for channel in $export_channels | |
do | |
# Skip channels with "cancel" in the name (case-insensitive) | |
if [[ "${channel,,}" == *cancel* ]]; then | |
printf "\nSkipping channel #%s due to filter 'cancel*'\n" "$channel" | |
continue | |
fi | |
if [[ -d "$channel" ]] | |
then | |
printf "\n============================================\nLooking into #$channel...\n============================================\n" | |
for file in "$channel"/*.json | |
do | |
(( $loglevel >= 1 )) && printf "Checking channel file '$file'\n" | |
for a in $(cat $file | jq -c '.[].files[]? | [.file_access, .name, .is_external, .filetype, .timestamp, .url_private_download, .external_url, .url_private] | del(..|nulls)' | sed 's/ //g') | |
do | |
filetype=$(echo $a | jq -r '.[3]') | |
if [[ $filetype == $usertype ]] || [[ -z $usertype ]] || [[ -z $filetype ]] | |
then | |
file_access=$(echo $a | jq -r '.[0]') | |
if [[ $file_access == "not_visible" ]] | |
then | |
(( $loglevel >= 1 )) && printf "Skipping non visible file: $a\n" | |
continue | |
fi | |
filename_raw=$(echo $a | jq -r '.[1]') | |
if [[ ! -z $filename_raw ]] && [[ $filename_raw != "null" ]] | |
then | |
(( $loglevel >= 2 )) && printf "Checking file '$filename_raw': $a\n" | |
filename=$(echo $filename_raw | sed -e 'y/ฤรกวร รงฤรฉฤรจฤซรญวรฌลรณวรฒลซรบวรนววววรผฤรวรฤรฤรฤชรวรลรวรลชรวรววววร:/aaaaceeeeiiiioooouuuuuuuuuAAAAEEEEIIIIOOOOUUUUUUUUU_/') | |
filename="${filename##*/}" | |
ts=$(echo $a | jq -r '.[4]') | |
year=$(date -r $ts '+%Y') | |
month=$(date -r $ts '+%m') | |
# prefix filenames with date/time, as the same filename could be used | |
# multiple times in different slack messages with different file contents. | |
datetime=$(date -r $ts '+%Y%m%d-%H%M%S') | |
filename="${datetime}-${filename}" | |
# If the filename lacks an extension, append one based on filetype. | |
if [[ "$filename" != *.* ]] && [[ ! -z "$filetype" ]] && [[ "$filetype" != "null" ]]; then | |
filename="${filename}.${filetype}" | |
fi | |
base_folder="EXPORT/$channel/$year/$month" | |
file_path="$base_folder/$filename" | |
if [ -f "$file_path" ] && [[ $overwrite != true ]] | |
then | |
if [ ! -s "$file_path" ] | |
then | |
printf "$file_path exists, but file is empty. Retrying!\n" | |
rm "$file_path" | |
else | |
if [[ $silent != true ]] | |
then | |
printf "$file_path already exists in destination folder. Skipping!\n" | |
fi | |
continue | |
fi | |
fi | |
is_external=$(echo $a | jq -r '.[2]') | |
url=$(echo $a | jq -rc '.[5]') | |
if [[ $is_external == "true" ]] | |
then | |
if [ ! -f "${file_path%.*}".* ] | |
then | |
if [[ $link_external == "true" ]] | |
then | |
file_path_link="${file_path%.*}.html" | |
echo "download external file at <a href=\"$url\">$url</a> to <tt>$file_path</tt>" > "$file_path_link" | |
echo "Stored link to external file as link in '$file_path_link'" | |
else | |
echo "download external file at '$url' manually to '$file_path'" | |
fi | |
fi | |
continue | |
fi | |
mkdir -p "$base_folder" | |
printf "downloading to $file_path with $ts\n" | |
curl --progress-bar $url -o "$file_path" | |
fi | |
fi | |
done | |
done | |
fi | |
done | |
if [[ ! -z $userchannel ]] | |
then | |
exit 0 | |
fi | |
printf "\n~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~\nExporting canvases\n~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~\n" | |
root_folder_canvases="export/CANVAS" | |
for canvas in $(cat canvases.json | jq -c '.[] | [.name, .id, .filetype, .created, .url_private_download]') | |
do | |
filetype=$(echo $canvas | jq -r '.[2]') | |
if [[ $filetype != $usertype ]] && [[ ! -z $usertype ]] && [[ ! -z $filetype ]] | |
then | |
continue | |
fi | |
filename_raw=$(echo $canvas | jq -r '.[0]') | |
canvas_id=$(echo $canvas | jq -r '.[1]') | |
ts=$(echo $canvas | jq -r '.[3]') | |
year=$(date -r $ts '+%Y') | |
month=$(date -r $ts '+%m') | |
datetime=$(date -r $ts '+%Y%m%d-%H%M%S') | |
filename="${datetime}_${canvas_id}-${filename_raw}" | |
# Append file extension if missing and filetype is available | |
if [[ "$filename" != *.* ]] && [[ ! -z "$filetype" ]] && [[ "$filetype" != "null" ]]; then | |
filename="${filename}.${filetype}" | |
fi | |
file_path="$root_folder_canvases/$filename" | |
if [ -f "$file_path" ] && [[ $overwrite != true ]] | |
then | |
if [[ $silent != true ]] | |
then | |
printf "$filename already exists in destination folder. Skipping!\n" | |
fi | |
continue | |
fi | |
mkdir -p "$root_folder_canvases" | |
url=$(echo $canvas | jq -rc '.[4]') | |
printf "downloading to $file_path with $ts\n" | |
curl --progress-bar "$url" -o "$file_path" | |
done | |
printf "\n~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~\nExporting avatars\n~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~\n" | |
root_folder_users="export/USER" | |
IFS=$'\n' | |
for user in $(cat users.json | jq -c '.[] | [.name, .profile]') | |
do | |
user_name=$(echo $user | jq -r '.[0]') | |
profile=$(echo $user | jq -rc '.[1]') | |
root_folder_user="$root_folder_users/$user_name" | |
mkdir -p "$root_folder_user" | |
for image in $(echo $profile | jq -rc 'to_entries[] | select(.key | startswith("image")) | select(.value != "") | [.key, .value]') | |
do | |
image_name=$(echo $image | jq -rc '.[0]') | |
image_path="$root_folder_user/$image_name.png" | |
if [ -f "$image_path" ] && [[ $overwrite != true ]] | |
then | |
if [[ $silent != true ]] | |
then | |
printf "$image_path already exists in destination folder. Skipping!\n" | |
fi | |
continue | |
fi | |
image_url=$(echo $image | jq -rc '.[1]') | |
echo "Downloading $user_name/$image_name: $image_url" | |
curl --progress-bar "$image_url" -o "$image_path" | |
done | |
done |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
๐ฅ How to Run
slack-files-downloader.sh
on Windows Using WSLThis guide provides step-by-step instructions for setting up and running the
slack-files-downloader.sh
script on Windows using Windows Subsystem for Linux (WSL).๐น Step 1: Install Windows Subsystem for Linux (WSL)
wsl --update
๐น Step 2: Install Required Dependencies (
jq
&curl
)jq
andcurl
(needed for the script):exit
๐น Step 3: Prepare the Bash Script
slack-files-downloader.sh
and save it in a directory like:๐น Step 4: Run the Script in WSL
cd /mnt/c/Users/YourName/Downloads
๐น Step 5: Verify Downloads
export/
folder.๐ง Troubleshooting
โ WSL is Not Found or Ubuntu Doesn't Start
โ
jq: command not found
jq
is installed:โ
\r
Errors (Windows Line Endings Issue)slack-files-downloader.sh
in VS Code.CRLF
(bottom right corner).โ Conclusion
By following these steps, you can successfully run the
slack-files-downloader.sh
script on Windows using WSL. ๐If you run into any issues, feel free to open a discussion or issue! Keep in mind I used ChatGPT to accomplish this and this is also what I used to generate this same guide.