Skip to content

Instantly share code, notes, and snippets.

@designfrontier
Created February 9, 2026 23:08
Show Gist options
  • Select an option

  • Save designfrontier/7e588e35ac942ae087cc2ec789d7c2f4 to your computer and use it in GitHub Desktop.

Select an option

Save designfrontier/7e588e35ac942ae087cc2ec789d7c2f4 to your computer and use it in GitHub Desktop.
#!/usr/bin/env bash
# https://id.atlassian.com/manage-profile/security/api-tokens
# for getting your tokens :pointup:
# Required env vars:
# JIRA_TOKEN=token from above here
# JIRA_USERNAME=voze email
# JIRA_BASE_URL=https://voze.atlassian.net
# JIRA_TICKET_TYPES=("Tech Debt Task" "Bug" "Task" "Support Request")
# JIRA_PROJECTS=("VE")
# put these somewhere that gets them in the env vars before running the script
JIRA_TEAMS=("Doritos Locos" "Baja Blast" "Bug Triage" "Cheesy Gordita Crunch" "Diablo Sauce")
get_team_id() {
case "$1" in
"Doritos Locos") echo "dbf42f58-9e39-4323-bd1d-dd4e349ef535" ;;
"Baja Blast") echo "ad1beac6-e009-477c-a3d6-7ba9bfae3007" ;;
"Bug Triage") echo "072cf690-bba8-4376-98db-6af85ef892de" ;;
"Cheesy Gordita Crunch") echo "6c7c02ac-fb09-4e5a-9e2e-64747d35ed6d" ;;
"Diablo Sauce") echo "b406269c-77dd-4c7d-bc78-b462d1ed0395" ;;
esac
}
show_help() {
cat << EOF
create-jira - Create Jira tickets from command line or interactively
USAGE:
create-jira [OPTIONS]
create-jira SUMMARY DESCRIPTION TEAM [TYPE] [PROJECT]
OPTIONS:
-h, --help Show this help message
MODES:
Interactive Mode (no arguments):
create-jira
Prompts for all required information interactively.
CLI Mode (with arguments):
create-jira "Summary" "Description" "Team" ["Type"] ["Project"]
Creates ticket directly with provided arguments.
Type defaults to "Task", Project defaults to "VE".
ARGUMENTS:
SUMMARY Brief one-line summary of the ticket
DESCRIPTION Detailed description (can be multi-line)
TEAM Assigned team (required)
Valid teams: Doritos Locos, Baja Blast, Bug Triage,
Cheesy Gordita Crunch, Diablo Sauce
TYPE Ticket type (optional, default: Task)
Valid types: Tech Debt Task, Bug, Task, Support Request
PROJECT Project key (optional, default: VE)
Valid projects: VE
EXAMPLES:
# Interactive mode
create-jira
# Create a Task (default type) in VE (default project)
create-jira "Fix login bug" "Users unable to login after 2FA" "Baja Blast"
# Create a Bug in VE
create-jira "Fix login bug" "Users unable to login" "Bug Triage" "Bug"
# Create a Tech Debt Task with full specification
create-jira "Refactor auth module" "Split into smaller functions" "Doritos Locos" "Tech Debt Task" "VE"
# Read description from file
create-jira "Migrate SQL view" "\$(cat description.txt)" "Cheesy Gordita Crunch" "Tech Debt Task"
ENVIRONMENT VARIABLES:
Required (should be in ~/.localvars):
JIRA_TOKEN API token from Atlassian
JIRA_USERNAME Your Voze email
JIRA_BASE_URL https://voze.atlassian.net
JIRA_TICKET_TYPES Array of valid ticket types
JIRA_PROJECTS Array of valid project keys
REQUIREMENTS:
- jq (install with: brew install jq)
- curl
- Valid Jira API credentials in ~/.localvars
OUTPUT:
On success, prints ticket key and URL:
✓ Ticket created: VE-1234
https://voze.atlassian.net/browse/VE-1234
On error, prints HTTP status and error details.
EOF
exit 0
}
# Check for help flag
if [[ "$1" == "-h" || "$1" == "--help" ]]; then
show_help
fi
source ~/.localvars
# Check if jq is available (required for proper JSON encoding)
if ! command -v jq &> /dev/null; then
echo "Error: jq is required but not installed. Install with: brew install jq"
exit 1
fi
# Check if arguments provided (CLI mode)
if [ $# -ge 3 ]; then
# CLI mode
SUMMARY="$1"
DESCRIPTION="$2"
TEAM="$3"
TYPE="${4:-Task}" # Default to Task
PROJECT="${5:-VE}" # Default to VE
# Validate team
VALID_TEAM=false
for valid_team in "${JIRA_TEAMS[@]}"; do
if [ "$TEAM" = "$valid_team" ]; then
VALID_TEAM=true
break
fi
done
if [ "$VALID_TEAM" = false ]; then
echo "Error: Invalid team '$TEAM'. Must be one of: ${JIRA_TEAMS[*]}"
exit 1
fi
# Validate type
VALID_TYPE=false
for valid_type in "${JIRA_TICKET_TYPES[@]}"; do
if [ "$TYPE" = "$valid_type" ]; then
VALID_TYPE=true
break
fi
done
if [ "$VALID_TYPE" = false ]; then
echo "Error: Invalid type '$TYPE'. Must be one of: ${JIRA_TICKET_TYPES[*]}"
exit 1
fi
# Validate project
VALID_PROJECT=false
for valid_project in "${JIRA_PROJECTS[@]}"; do
if [ "$PROJECT" = "$valid_project" ]; then
VALID_PROJECT=true
break
fi
done
if [ "$VALID_PROJECT" = false ]; then
echo "Error: Invalid project '$PROJECT'. Must be one of: ${JIRA_PROJECTS[*]}"
exit 1
fi
else
# Interactive mode (original behavior)
GIT_MESSAGE=$(git log -n 1)
read -p "Brief Summary:" SUMMARY
read -p "Description:" DESCRIPTION
echo ""
echo 'Please enter ticket type: '
select T in "${JIRA_TICKET_TYPES[@]}"
do
case $T in
"Tech Debt Task")
TYPE="Tech Debt Task"; break
;;
"Bug")
TYPE="Bug"; break
;;
"Task")
TYPE="Task"; break
;;
"Support Request")
TYPE="Support Request"; break
;;
*) echo "invalid option $REPLY";;
esac
done
echo ""
echo 'Please select team: '
select TM in "${JIRA_TEAMS[@]}"
do
if [[ -n "$TM" ]]; then
TEAM="$TM"; break
else
echo "invalid option $REPLY"
fi
done
echo ""
echo 'Please select project: '
select P in "${JIRA_PROJECTS[@]}"
do
case $P in
"VE")
PROJECT="VE"; break
;;
*) echo "invalid option $REPLY";;
esac
done
fi
# Resolve team name to ID
TEAM_ID=$(get_team_id "$TEAM")
# Build JSON using jq for proper escaping
JSON=$(jq -n \
--arg project "$PROJECT" \
--arg summary "$SUMMARY" \
--arg description "$DESCRIPTION" \
--arg type "$TYPE" \
--arg team_id "$TEAM_ID" \
'{
fields: {
project: {key: $project},
summary: $summary,
description: $description,
issuetype: {name: $type},
customfield_10001: $team_id
}
}')
# Make API request and capture both body and status code
RESPONSE=$(curl -sS -w "\n%{http_code}" \
-u "$JIRA_USERNAME:$JIRA_TOKEN" \
-X POST \
--data "$JSON" \
-H "Content-Type: application/json" \
"$JIRA_BASE_URL/rest/api/2/issue/")
HTTP_CODE=$(echo "$RESPONSE" | tail -1)
BODY=$(echo "$RESPONSE" | sed '$d')
# Check if request was successful
if [ "$HTTP_CODE" = "201" ]; then
KEY=$(echo "$BODY" | jq -r '.key')
echo "✓ Ticket created: $KEY"
echo "$JIRA_BASE_URL/browse/$KEY"
# Only try to open if we're in an interactive terminal
if [ -t 0 ]; then
open "$JIRA_BASE_URL/browse/$KEY" 2>/dev/null || true
fi
else
echo "Error creating ticket (HTTP $HTTP_CODE):"
echo "$BODY" | jq -r '.errorMessages[]?, .errors | to_entries[]? | "\(.key): \(.value)"' 2>/dev/null || echo "$BODY"
exit 1
fi
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment