Skip to content

Instantly share code, notes, and snippets.

@rbf
Last active December 20, 2015 10:48
Show Gist options
  • Save rbf/6117917 to your computer and use it in GitHub Desktop.
Save rbf/6117917 to your computer and use it in GitHub Desktop.
Shell tool to get the permalink of a gist raw file at given commit or tag at https://gist.github.com.

Description

Shell tool to get the permalink of a gist raw file at given commit or tag at https://gist.github.com.

Installation

To install this tool (v2.0) directly to your /usr/local/bin you can use following command (you might need to be root to execute it):

mkdir -p /usr/local/bin && curl -L "https://gist.github.com/rbf/6117917/raw/8f78504ace67d36bfb7f7f4cb703cc51678a5fbf/gist-raw-url" -o /usr/local/bin/gist-raw-url && chmod +x /usr/local/bin/gist-raw-url

To directly generate the wanted permalink without installing or downloading the code, you can directly use this command, followed by the name of the file you want the permalink for:

bash <(curl -sSL "https://gist.github.com/rbf/6117917/raw/8f78504ace67d36bfb7f7f4cb703cc51678a5fbf/gist-raw-url") <filename>

Change log

v2.0 (11nov2013)

  • [change] Update name from gist-url-raw to gist-raw-url.
  • [change] Update to new URL format used by GitHub for raw files.
  • [bugfix] Fix for file names with spaces.

v1.3 (05aug2013)

  • [bugfix] Add prefix to check for anonymously cloned gists.
  • [bugfix] Remove -e and -n flags and \r chars in echo commands, since not consistent across shells.
  • [new] Add a check to verify that git is installed.
  • [change] Small tweak to help message.
  • [change] Add hint to read the --help info when no file is specified.

v1.2.1 (31jul2013)

  • [bugfix] Fix command name value on help and version outputs when installed in '/usr/local/bin'

v1.2 (31jul2013)

  • [new] Add --help and --version.
  • [new] Enhance test to check if we are in a gist repo.
  • [change] Make gist shell agnostic (remove bashisms).

v1.1 (31jul2013)

  • [new] Add when file was first seen in the commit history.

v1.0.1 (31jul2013)

  • [new] Verify if we are in a gist repo.

v1.0 (31jul2013)

  • Initial version.
#!/bin/sh
# The MIT License (MIT)
#
# Copyright (c) 2013 https://gist.github.com/rbf
#
# Permission is hereby granted, free of charge, to any person obtaining a copy of
# this software and associated documentation files (the "Software"), to deal in
# the Software without restriction, including without limitation the rights to
# use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of
# the Software, and to permit persons to whom the Software is furnished to do so,
# subject to the following conditions:
#
# The above copyright notice and this permission notice shall be included in all
# copies or substantial portions of the Software.
#
# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS
# FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR
# COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
# IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
# CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
### File info:
GUR_VERSION="v2.1-SNAPSHOT"
GUR_SOURCE="https://gist.github.com/rbf/6117917/raw/gist-raw-url"
GUR_DOC="https://gist.github.com/rbf/6117917"
GUR_INSTALL_PATH="/usr/local/bin/"
###
GUR_COMMAND_DEFAULT_NAME=$(basename "${GUR_SOURCE}")
GUR_COMMAND_NAME="${0#${GUR_INSTALL_PATH}}"
GUR_COMMAND_NAME="${GUR_COMMAND_NAME##/dev/fd/*}" # When using it in a piped mode, the pipe filename tends to be '/dev/fd/63'
GUR_COMMAND_NAME="${GUR_COMMAND_NAME:-${GUR_COMMAND_DEFAULT_NAME}}"
if [ "${1}" == "--help" ] || [ "${1}" == "-h" ] || [ "${1}" == "-?" ]
then
echo "Returns the permalink URL to the raw version of a gist's file at a given commit."
echo "Usage: ${GUR_COMMAND_NAME} <filename> [<committish> [<remote>]]"
echo " <filename> The file to generate the permalink URL for."
echo " <committish> The committish object name (like e.g. a commit hash or a tag name) of the target file version."
echo " Defaults to last annotated tag, or last commit if no tag found. Using 'HEAD' as a '<committish>' object, "
echo " generates a permalik URL that will point always to the last committed version of the file."
echo " <remote> The remote to get the URL from. In most cases this doesn't need to be specified, since it will be often 'origin'."
echo " Defaults to 'origin'."
echo "For more info visit ${GUR_DOC}"
exit 0
elif [ "${1}" == "--version" ] || [ "${1}" == "-v" ]
then
echo "${GUR_COMMAND_NAME} ${GUR_VERSION}"
exit 0
fi
[ -z "$(which git)" ] && echo "It doesn't seem to be git installed in this system, or at least is not reachable in the PATH." && exit 0
[ -e .git/config ] && gistid="$(git config --get remote.${3:-origin}.url)"
gistid="${gistid#https://gist.github.com/}"
gistid="${gistid#git://github.com/}" # Anonymously cloned gist
gistid="${gistid#git@gist.github.com:}"
gistid="${gistid#git@github.com:}"
gistid="${gistid%.git}"
[ -z "${gistid##*[!0-9]*}" ] && echo "It doesn't seem to be a gist repo here." && exit 0
if [ ! "$1" ]
then
echo "Specify the file to get the permalink for. Try e.g. with following command:"
echo " ${GUR_COMMAND_NAME} $(git ls-tree --name-only HEAD | head -1)"
echo "For more info type:"
echo " ${GUR_COMMAND_NAME} --help"
exit 1
fi
commit=${2:-$(git describe --always --abbrev=0)}
gitblob="$(git ls-tree ${commit} "${1}")"
[ ! $? -eq 0 ] && echo "'${commit}' is not a committish object name, like e.g. a commit hash or a tag name." && exit 1
[ "$(git tag)" ] && committype="last annotated tag" || committype="last commit" && commit=${commit:0:7}
GUR_GIST_API_URL="https://api.github.com/gists/${gistid}"
GUR_GIST_API_JSON="$(curl -siL ${GUR_GIST_API_URL})"
GUR_GIST_API_CALL_EXIT_CODE="$?"
if [ "${GUR_GIST_API_CALL_EXIT_CODE}" != "0" ]
then
# Possibly no internet connection
echo "GitHub API couldn't be reached at ${GUR_GIST_API_URL}"
exit 1
elif [ -z "$(echo "${GUR_GIST_API_JSON}" | grep "Status.*20*")" ]
then
# Possibly wrong gist id fetched
echo "Oups! Something went wrong while trying to find out more about the gist ${gistid} on the URL ${GUR_GIST_API_URL}"
exit 1
fi
GUR_BASE_GIST_URL="$( echo "${GUR_GIST_API_JSON}" | grep "raw_url" | head -1 | sed -e "s|.*\(http.*raw\).*|\1|")"
url=$(echo "${gitblob}" | sed "s|.* .* \(.*\)[[:space:]]${1}|${GUR_BASE_GIST_URL}/\1/${1}|" | sed "s| |%20|g")
if [ "${url}" ]
then
if [ "${2}" == "HEAD" ]
then
echo "${GUR_BASE_GIST_URL}/${1}"
exit 0
fi
[ ! $2 ] && echo "Permalink to file '${1}' at ${committype} '${commit}':"
echo "${url}"
else
firstseencommit=$(git log --reverse --format="%H" -- "${1}" | head -1)
lastseencommit=$(git log -1 --format="%H" -- "${1}")
[ "$(git ls-tree --name-only HEAD "${1}")" ] && currentlypresent=true
if [ ${lastseencommit} ]
then
firstseentag=$(git describe --always --abbrev=7 ${firstseencommit})
lastseentag=$(git describe --always --abbrev=7 ${lastseencommit}^)
echo "File '${1}' not found at $([ ${2} ] && echo "commit" || echo "${committype}") '${commit}'."
echo "Try the following command to get a list of candidate files at this point:"
echo " git ls-tree --name-only ${commit}"
echo "The file was first seen at commit '${firstseentag}' $(git log -1 --format="%cr" "${firstseentag}"),"
if [ $currentlypresent ]
then
echo "was last modified at commit '${lastseentag}' $(git log -1 --format="%cr" "${lastseentag}"), and is currently still present at HEAD."
else
echo "and last seen at commit '${lastseentag}' $(git log -1 --format="%cr" "${lastseentag}")."
fi
echo "Try the following command to get a the URL to the raw file at this first and last commit points:"
echo " ${GUR_COMMAND_NAME} ${1} ${firstseentag}"
echo " ${GUR_COMMAND_NAME} ${1} ${lastseentag}"
else
echo "File '${1}' not found in this repository's history."
echo "Try the following command to get a list of candidate files at the $([ ${2} ] && echo "commit" || echo "${committype}") '${commit}':"
echo " git ls-tree --name-only ${commit}"
fi
fi
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment