mirror of
https://github.com/NATroutter/egg-hytale.git
synced 2026-03-01 11:21:13 +03:00
250 lines
9.7 KiB
Bash
250 lines
9.7 KiB
Bash
# Function to check if cached tokens exist
|
|
check_cached_tokens() {
|
|
if [ -f "$AUTH_CACHE_FILE" ]; then
|
|
# Check if jq is available
|
|
if ! command -v jq &> /dev/null; then
|
|
logger warn "jq not found, cannot use cached tokens"
|
|
return 1
|
|
fi
|
|
|
|
# Validate JSON format
|
|
if ! jq empty "$AUTH_CACHE_FILE" 2>/dev/null; then
|
|
logger warn "Invalid cached token file, removing..."
|
|
rm "$AUTH_CACHE_FILE"
|
|
return 1
|
|
fi
|
|
|
|
# Check if required keys exist
|
|
REFRESH_TOKEN_EXISTS=$(jq -r 'has("refresh_token")' "$AUTH_CACHE_FILE")
|
|
PROFILE_UUID_EXISTS=$(jq -r 'has("profile_uuid")' "$AUTH_CACHE_FILE")
|
|
|
|
if [ "$REFRESH_TOKEN_EXISTS" != "true" ] || [ "$PROFILE_UUID_EXISTS" != "true" ]; then
|
|
logger warn "Cached token file missing required keys, removing..."
|
|
rm "$AUTH_CACHE_FILE"
|
|
return 1
|
|
fi
|
|
|
|
logger success "Found cached authentication tokens"
|
|
return 0
|
|
fi
|
|
return 1
|
|
}
|
|
|
|
|
|
|
|
# Function to load cached tokens (refresh_token + profile_uuid only)
|
|
load_cached_tokens() {
|
|
REFRESH_TOKEN=$(jq -r '.refresh_token' "$AUTH_CACHE_FILE")
|
|
PROFILE_UUID=$(jq -r '.profile_uuid' "$AUTH_CACHE_FILE")
|
|
|
|
# Validate required tokens are present
|
|
if [ -z "$REFRESH_TOKEN" ] || [ "$REFRESH_TOKEN" = "null" ] || \
|
|
[ -z "$PROFILE_UUID" ] || [ "$PROFILE_UUID" = "null" ]; then
|
|
logger error "Incomplete cached tokens, re-authenticating..."
|
|
rm "$AUTH_CACHE_FILE"
|
|
return 1
|
|
fi
|
|
|
|
logger success "Loaded cached refresh token + profile UUID"
|
|
return 0
|
|
}
|
|
|
|
|
|
|
|
# Function to refresh access token using cached refresh token
|
|
refresh_access_token() {
|
|
logger info "Refreshing access token..."
|
|
|
|
TOKEN_RESPONSE=$(curl -s -X POST "https://oauth.accounts.hytale.com/oauth2/token" \
|
|
-H "Content-Type: application/x-www-form-urlencoded" \
|
|
-d "client_id=hytale-server" \
|
|
-d "grant_type=refresh_token" \
|
|
-d "refresh_token=$REFRESH_TOKEN")
|
|
|
|
ERROR=$(echo "$TOKEN_RESPONSE" | jq -r '.error // empty')
|
|
if [ -n "$ERROR" ]; then
|
|
logger error "Failed to refresh access token: $ERROR"
|
|
return 1
|
|
fi
|
|
|
|
ACCESS_TOKEN=$(echo "$TOKEN_RESPONSE" | jq -r '.access_token')
|
|
NEW_REFRESH_TOKEN=$(echo "$TOKEN_RESPONSE" | jq -r '.refresh_token // empty')
|
|
|
|
if [ -z "$ACCESS_TOKEN" ] || [ "$ACCESS_TOKEN" = "null" ]; then
|
|
logger error "No access token in refresh response"
|
|
return 1
|
|
fi
|
|
|
|
# Update refresh token if a new one was provided
|
|
if [ -n "$NEW_REFRESH_TOKEN" ] && [ "$NEW_REFRESH_TOKEN" != "null" ]; then
|
|
REFRESH_TOKEN="$NEW_REFRESH_TOKEN"
|
|
fi
|
|
|
|
logger success "Access token refreshed"
|
|
return 0
|
|
}
|
|
|
|
|
|
|
|
# Function to create a new game session
|
|
create_game_session() {
|
|
logger info "Creating game server session..."
|
|
|
|
SESSION_RESPONSE=$(curl -s -X POST "https://sessions.hytale.com/game-session/new" \
|
|
-H "Authorization: Bearer $ACCESS_TOKEN" \
|
|
-H "Content-Type: application/json" \
|
|
-d "{\"uuid\": \"$PROFILE_UUID\"}")
|
|
|
|
# Validate JSON response
|
|
if ! echo "$SESSION_RESPONSE" | jq empty 2>/dev/null; then
|
|
logger error "Invalid JSON response from game session creation"
|
|
logger info "Response: $SESSION_RESPONSE"
|
|
return 1
|
|
fi
|
|
|
|
# Extract session and identity tokens
|
|
SESSION_TOKEN=$(echo "$SESSION_RESPONSE" | jq -r '.sessionToken')
|
|
IDENTITY_TOKEN=$(echo "$SESSION_RESPONSE" | jq -r '.identityToken')
|
|
|
|
if [ -z "$SESSION_TOKEN" ] || [ "$SESSION_TOKEN" = "null" ]; then
|
|
logger error "Failed to create game server session"
|
|
logger info "Response: $SESSION_RESPONSE"
|
|
return 1
|
|
fi
|
|
|
|
logger success "Game server session created successfully!"
|
|
return 0
|
|
}
|
|
|
|
# Function to save authentication tokens (refresh_token + profile_uuid only)
|
|
save_auth_tokens() {
|
|
|
|
# Create auth cache file (only in standard mode, not GSP mode)
|
|
if [ ! -f "$AUTH_CACHE_FILE" ]; then
|
|
logger info "Creating auth cache file..."
|
|
touch $AUTH_CACHE_FILE
|
|
fi
|
|
|
|
cat > "$AUTH_CACHE_FILE" << EOF
|
|
{
|
|
"refresh_token": "$REFRESH_TOKEN",
|
|
"profile_uuid": "$PROFILE_UUID",
|
|
"timestamp": $(date +%s)
|
|
}
|
|
EOF
|
|
logger info "Refresh token cached for future use"
|
|
}
|
|
|
|
|
|
|
|
# Function to perform full authentication
|
|
perform_authentication() {
|
|
logger info "Obtaining authentication tokens..."
|
|
|
|
# Step 1: Request device code
|
|
AUTH_RESPONSE=$(curl -s -X POST "https://oauth.accounts.hytale.com/oauth2/device/auth" \
|
|
-H "Content-Type: application/x-www-form-urlencoded" \
|
|
-d "client_id=hytale-server" \
|
|
-d "scope=openid offline auth:server")
|
|
|
|
# Extract device_code and verification_uri_complete using jq
|
|
DEVICE_CODE=$(echo "$AUTH_RESPONSE" | jq -r '.device_code')
|
|
VERIFICATION_URI=$(echo "$AUTH_RESPONSE" | jq -r '.verification_uri_complete')
|
|
POLL_INTERVAL=$(echo "$AUTH_RESPONSE" | jq -r '.interval')
|
|
|
|
# Display authentication banner
|
|
echo " "
|
|
printc "{MAGENTA}╔═════════════════════════════════════════════════════════════════════════════╗"
|
|
printc "{MAGENTA}║ {BLUE}HYTALE SERVER AUTHENTICATION REQUIRED {MAGENTA}║"
|
|
printc "{MAGENTA}╠═════════════════════════════════════════════════════════════════════════════╣"
|
|
printc "{MAGENTA}║ ║"
|
|
printc "{MAGENTA}║ {CYAN}Please authenticate the server by visiting the following URL: {MAGENTA}║"
|
|
printc "{MAGENTA}║ ║"
|
|
printc "{MAGENTA}║ {YELLOW}$VERIFICATION_URI {MAGENTA}║"
|
|
printc "{MAGENTA}║ ║"
|
|
printc "{MAGENTA}║ {CYAN}1. Click the link above or copy it to your browser {MAGENTA}║"
|
|
printc "{MAGENTA}║ {CYAN}2. Sign in with your Hytale account {MAGENTA}║"
|
|
printc "{MAGENTA}║ {CYAN}3. Authorize the server {MAGENTA}║"
|
|
printc "{MAGENTA}║ ║"
|
|
printc "{MAGENTA}║ {CYAN}Waiting for authentication... {MAGENTA}║"
|
|
printc "{MAGENTA}║ ║"
|
|
printc "{MAGENTA}╚═════════════════════════════════════════════════════════════════════════════╝"
|
|
printc " "
|
|
|
|
# Step 2: Poll for access token
|
|
ACCESS_TOKEN=""
|
|
while [ -z "$ACCESS_TOKEN" ]; do
|
|
sleep $POLL_INTERVAL
|
|
|
|
TOKEN_RESPONSE=$(curl -s -X POST "https://oauth.accounts.hytale.com/oauth2/token" \
|
|
-H "Content-Type: application/x-www-form-urlencoded" \
|
|
-d "client_id=hytale-server" \
|
|
-d "grant_type=urn:ietf:params:oauth:grant-type:device_code" \
|
|
-d "device_code=$DEVICE_CODE")
|
|
|
|
# Check if we got an error
|
|
ERROR=$(echo "$TOKEN_RESPONSE" | jq -r '.error // empty')
|
|
|
|
if [ "$ERROR" = "authorization_pending" ]; then
|
|
logger info "Still waiting for authentication..."
|
|
continue
|
|
elif [ -n "$ERROR" ]; then
|
|
logger error "Authentication error: $ERROR"
|
|
exit 1
|
|
else
|
|
# Successfully authenticated
|
|
ACCESS_TOKEN=$(echo "$TOKEN_RESPONSE" | jq -r '.access_token')
|
|
REFRESH_TOKEN=$(echo "$TOKEN_RESPONSE" | jq -r '.refresh_token')
|
|
echo ""
|
|
logger success "Authentication successful!"
|
|
echo ""
|
|
fi
|
|
done
|
|
|
|
# Fetch available game profiles
|
|
logger info "Fetching game profiles..."
|
|
|
|
PROFILES_RESPONSE=$(curl -s -X GET "https://account-data.hytale.com/my-account/get-profiles" \
|
|
-H "Authorization: Bearer $ACCESS_TOKEN")
|
|
|
|
# Check if profiles list is empty
|
|
PROFILES_COUNT=$(echo "$PROFILES_RESPONSE" | jq '.profiles | length')
|
|
|
|
if [ "$PROFILES_COUNT" -eq 0 ]; then
|
|
logger error "No game profiles found. You need to purchase Hytale to run a server."
|
|
exit 1
|
|
fi
|
|
|
|
# Select profile based on GAME_PROFILE variable
|
|
if [ -n "$GAME_PROFILE" ]; then
|
|
# User specified a profile username, find matching UUID
|
|
logger info "Looking for profile: $GAME_PROFILE"
|
|
PROFILE_UUID=$(echo "$PROFILES_RESPONSE" | jq -r ".profiles[] | select(.username == \"$GAME_PROFILE\") | .uuid")
|
|
|
|
if [ -z "$PROFILE_UUID" ] || [ "$PROFILE_UUID" = "null" ]; then
|
|
logger error "Profile '$GAME_PROFILE' not found."
|
|
logger info "Available profiles:"
|
|
logger success "$PROFILES_RESPONSE" | jq -r '.profiles[] | " - \(.username)"'
|
|
exit 1
|
|
fi
|
|
|
|
logger success "Using profile: $GAME_PROFILE (UUID: $PROFILE_UUID)"
|
|
else
|
|
# Use first profile from the list
|
|
PROFILE_UUID=$(echo "$PROFILES_RESPONSE" | jq -r '.profiles[0].uuid')
|
|
PROFILE_USERNAME=$(echo "$PROFILES_RESPONSE" | jq -r '.profiles[0].username')
|
|
|
|
logger success "Using default profile: $PROFILE_USERNAME (UUID: $PROFILE_UUID)"
|
|
fi
|
|
|
|
echo ""
|
|
|
|
# Save refresh token + profile for future use
|
|
save_auth_tokens
|
|
|
|
# Create game server session
|
|
if ! create_game_session; then
|
|
exit 1
|
|
fi
|
|
echo ""
|
|
} |