#!/bin/zsh

cd ${0:a:h}

# iOS Social App Patch Setup Script
# Usage: ./ios/setup.zsh [patch|reset]

# Cross-platform sed (macOS vs Linux)
function sediment() {
	if [[ "$OSTYPE" == "darwin"* ]]; then
		sed -i '' "$@"
	else
		sed -i "$@"
	fi
}

# Arrays for patch management
typeset -a FAILED_PATCHES

# Patch file lists for iOS
typeset -a PATCH_FILES_IOS
PATCH_FILES_IOS=(
	"001-social-app-ios-config.patch"
	"002-social-app-ios-lib.patch"
	"003-social-app-ios-view.patch"              # Splash + UserAvatar (Logo/Logotype → copy)
	"004-social-app-ios-core.patch"
	"005-social-app-ios-screens.patch"            # AboutSettings + Takendown + RightNav (PrivacyPolicy/TOS → copy)
	"006-social-app-ios-shell.patch"
	"007-social-app-ios-misc.patch"
	"009-social-app-ios-license.patch"
	"010-social-app-ios-remove-contact-support.patch"
	"011-social-app-ios-splash-license-footer.patch"
	"013-social-app-ios-settings-remove-help.patch"
	"019-social-app-ios-entitlements-plugin.patch"
	"020-social-app-ios-bypass-age-assurance.patch"
	"021-social-app-ios-clean-feed.patch"          # DiscoverFallback + Empty/End + PostFeed (merged 040)
	"022-social-app-ios-bskyweb.patch"             # bskyweb routes + templates (merged 025)
	"024-social-app-ios-disable-external-services.patch"
	"027-social-app-ios-remove-birthdate.patch"
	"028-social-app-ios-remove-discover.patch"     # Explore + Feeds (merged 029)
	"032-social-app-ios-feed-loggedout.patch"
	"033-social-app-ios-hide-profile-tabs.patch"
	"036-social-app-ios-homeheader-loggedout.patch"
	"037-social-app-ios-disable-contacts-nux.patch"
	"038-social-app-ios-profile-services.patch"    # ProfileServiceLinks + ProfileAtLinks (merged 042)
	"039-social-app-ios-hide-feed-controls.patch"
	"041-social-app-ios-splash-custom.patch"        # signin-button + splash-video (merged 044)
	"045-social-app-ios-composer-cancel.patch"
	"046-social-app-ios-null-url-guards.patch"
	"047-social-app-ios-dynamic-service.patch"   # Dynamic proxy/notif per account (syu.is vs bsky.social)
	"048-social-app-ios-dm-grapheme-limit.patch"
)

function ios-env() {
	d=${0:a:h:h}
	patching_dir=${0:a:h}/patching
	target_dir=$d/repos/social-app
}

# Common patch function with status detection
function apply-patch() {
	local patch_name=$1
	local target_dir=$2
	local patch_file=$3

	echo "━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━"
	echo "📝 Patch: ${patch_name}"
	echo "   Target: ${target_dir}"
	echo "   File: ${patch_file}"

	pushd ${target_dir} > /dev/null

	# Check if patch can be applied (forward dry-run succeeds)
	if patch --dry-run -p1 < ${patch_file} > /dev/null 2>&1; then
		echo "🔧 Applying patch..."
		if patch -p1 < ${patch_file}; then
			echo "✅ Applied successfully"
			popd > /dev/null
			echo ""
			return 0
		else
			echo "❌ Failed to apply"
			FAILED_PATCHES+=("${patch_name} (${patch_file})")
			popd > /dev/null
			echo ""
			return 1
		fi
	else
		echo "⚠️  Cannot apply - file may have been modified"
		echo "   Please check manually"
		FAILED_PATCHES+=("${patch_name} (${patch_file}) - file modified")
		popd > /dev/null
		echo ""
		return 1
	fi
}

function show-failed-patches() {
	if [ ${#FAILED_PATCHES[@]} -eq 0 ]; then
		echo ""
		echo "━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━"
		echo "✅ All patches applied successfully!"
		echo "━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━"
		echo ""
		return 0
	fi

	echo ""
	echo "━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━"
	echo "⚠️  FAILED PATCHES SUMMARY"
	echo "━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━"
	echo ""
	echo "The following patches could not be applied:"
	echo ""
	for failed_patch in "${FAILED_PATCHES[@]}"; do
		echo "  ❌ ${failed_patch}"
	done
	echo ""
	echo "━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━"
	echo ""
}

# Helper function for applying patches
function patch-apply() {
	local name=$1
	local patch_file=$2
	apply-patch "${name}" "$target_dir" "$patching_dir/${patch_file}"
}

# Generate build number from timestamp (YYMMDDHHMMSS)
function ios-generate-build-number() {
	local build_number=$(date +%y%m%d%H%M%S)
	local config_patch="$patching_dir/001-social-app-ios-config.patch"

	if [ -f "$config_patch" ]; then
		# Replace placeholder with timestamp
		sediment "s/__BUILD_NUMBER__/${build_number}/" "$config_patch"
		echo "━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━"
		echo "🔢 Build number: ${build_number}"
		echo ""
	fi
}

# Restore placeholder after patching (for git cleanliness)
function ios-restore-build-placeholder() {
	local config_patch="$patching_dir/001-social-app-ios-config.patch"

	if [ -f "$config_patch" ]; then
		# Restore placeholder for next build
		sediment "s/buildNumber: '[0-9]*'/buildNumber: '__BUILD_NUMBER__'/" "$config_patch"
	fi
}

# Auto-apply patches from list
function ios-patch-apply-all() {
	for filename in "${PATCH_FILES_IOS[@]}"; do
		local title="${filename%.*}"
		patch-apply "$title" "$filename"
	done

	# Patch @atproto/api lexicon: chat.bsky.convo maxGraphemes 1000 -> 10000
	local api_dir="$target_dir/node_modules/@atproto/api"
	local patch_file="$d/patching/230-atproto-api-chat-grapheme-limit.patch"
	if [ -d "$api_dir" ] && [ -f "$patch_file" ]; then
		if patch -f --dry-run -p1 -d "$api_dir" < "$patch_file" > /dev/null 2>&1; then
			patch -f -p1 -d "$api_dir" < "$patch_file" > /dev/null 2>&1
			echo "✅ Patched @atproto/api lexicons.js: chat.bsky.convo maxGraphemes 1000 → 10000"
		elif patch -f --dry-run -p1 -R -d "$api_dir" < "$patch_file" > /dev/null 2>&1; then
			echo "✅ @atproto/api lexicons.js: already patched"
		else
			echo "❌ @atproto/api lexicons.js: patch failed (upstream may have changed)"
		fi
	fi
}

# Copy new files that aren't in patches
function ios-copy-new-files() {
	echo "━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━"
	echo "📁 Copying new files..."

	# Copy all assets from ios/assets/ to repos/social-app/assets/
	if [ -d "$d/ios/assets" ]; then
		cp -rf "$d/ios/assets/"* "$target_dir/assets/"
		echo "✅ Copied all assets (including logo.png, app-icons)"
	fi

	# Generate app-icon.png (logo on #333 background) for app icon
	if [ -f "$d/ios/assets/logo.png" ]; then
		if command -v magick >/dev/null 2>&1; then
			magick -size 1024x1024 "xc:#333333" "$d/ios/assets/logo.png" -gravity center -composite "$target_dir/assets/app-icon.png"
			echo "✅ Generated app-icon.png (logo + #333 bg)"
		else
			echo "⚠️  ImageMagick not found, copying logo.png as app-icon.png fallback"
			cp "$d/ios/assets/logo.png" "$target_dir/assets/app-icon.png"
		fi
	fi

	# Copy License.tsx
	if [ -f "$patching_dir/License.tsx" ]; then
		mkdir -p "$target_dir/src/view/screens"
		cp "$patching_dir/License.tsx" "$target_dir/src/view/screens/License.tsx"
		echo "✅ Copied License.tsx"
	fi

	# Copy AppInfo.tsx
	if [ -f "$patching_dir/AppInfo.tsx" ]; then
		mkdir -p "$target_dir/src/view/screens"
		cp "$patching_dir/AppInfo.tsx" "$target_dir/src/view/screens/AppInfo.tsx"
		echo "✅ Copied AppInfo.tsx"
	fi

	# Copy Japanese locale (translation overrides)
	if [ -f "$patching_dir/ja-messages.po" ]; then
		cp "$patching_dir/ja-messages.po" "$target_dir/src/locale/locales/ja/messages.po"
		echo "✅ Copied ja-messages.po"
	fi

	# Copy splash video
	if [ -f "$d/ios/assets/splash/illustration-mobile.mp4" ]; then
		cp "$d/ios/assets/splash/illustration-mobile.mp4" "$target_dir/assets/splash/illustration-mobile.mp4"
		echo "✅ Copied splash video (illustration-mobile.mp4)"
	fi

	# Copy ProfileAtLinks.tsx
	if [ -f "$patching_dir/ProfileAtLinks.tsx" ]; then
		cp "$patching_dir/ProfileAtLinks.tsx" "$target_dir/src/screens/Profile/Header/ProfileAtLinks.tsx"
		echo "✅ Copied ProfileAtLinks.tsx"
	fi

	# Copy full-replacement files (upstream-proof: not affected by import changes)
	if [ -f "$patching_dir/Logo.tsx" ]; then
		cp "$patching_dir/Logo.tsx" "$target_dir/src/view/icons/Logo.tsx"
		echo "✅ Copied Logo.tsx"
	fi
	if [ -f "$patching_dir/Logotype.tsx" ]; then
		cp "$patching_dir/Logotype.tsx" "$target_dir/src/view/icons/Logotype.tsx"
		echo "✅ Copied Logotype.tsx"
	fi
	if [ -f "$patching_dir/PrivacyPolicy.tsx" ]; then
		cp "$patching_dir/PrivacyPolicy.tsx" "$target_dir/src/view/screens/PrivacyPolicy.tsx"
		echo "✅ Copied PrivacyPolicy.tsx"
	fi
	if [ -f "$patching_dir/TermsOfService.tsx" ]; then
		cp "$patching_dir/TermsOfService.tsx" "$target_dir/src/view/screens/TermsOfService.tsx"
		echo "✅ Copied TermsOfService.tsx"
	fi

	# Copy pre-generated favicons for bskyweb
	local favicon_src="$d/ios/assets/favicons"
	local bskyweb_static="$target_dir/bskyweb/static"
	if [ -d "$favicon_src" ] && [ -d "$bskyweb_static" ]; then
		cp -f "$d/ios/assets/logo.png" "$bskyweb_static/app.png"
		cp -f "$favicon_src/favicon.png" "$bskyweb_static/favicon.png"
		cp -f "$favicon_src/favicon-16x16.png" "$bskyweb_static/favicon-16x16.png"
		cp -f "$favicon_src/favicon-32x32.png" "$bskyweb_static/favicon-32x32.png"
		cp -f "$favicon_src/apple-touch-icon.png" "$bskyweb_static/apple-touch-icon.png"
		echo "✅ Copied favicons to bskyweb/static"
	fi

	# Compile locale if messages.po was copied
	if [ -f "$patching_dir/ja-messages.po" ]; then
		echo "🌐 Compiling locale..."
		pushd "$target_dir" > /dev/null
		yarn intl:compile 2>/dev/null && echo "✅ Compiled locale" || echo "⚠️  Locale compile skipped (yarn not ready)"
		popd > /dev/null
	fi

	echo ""
}

function ios-setup-clone() {
	if [ ! -d $target_dir ]; then
		echo "Error: social-app repository not found at $target_dir"
		echo "Please run install.zsh first to clone repositories"
		return 1
	fi
	echo "Repository found: $target_dir"
}

# Generate bskyweb templates from web/ build output
# web/ is the source of truth, bskyweb templates are generated from dist/aiat/
function ios-generate-bskyweb-templates() {
	echo "━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━"
	echo "🌐 Generating bskyweb templates from web/..."

	local web_dir="$d/../web"
	local templates="$target_dir/bskyweb/templates"
	local static_out="$target_dir/bskyweb/static"

	# Check if web directory exists
	if [ ! -d "$web_dir" ]; then
		echo "⚠️  web/ directory not found, skipping template generation"
		return 1
	fi

	# Build web
	echo "   Building web..."
	cd "$web_dir"
	npm install --silent 2>/dev/null
	npm run build --silent 2>/dev/null
	cd "$d"

	local dist_src="$web_dir/dist/aiat"
	local static_src="$web_dir/dist/aiat/static"

	# Check if build output exists
	if [ ! -d "$dist_src" ]; then
		echo "⚠️  web/dist/aiat not found, build may have failed"
		return 1
	fi

	# Create output directory
	mkdir -p "$templates"
	mkdir -p "$static_out"

	# Convert web/dist/aiat/ to bskyweb templates
	# Structure: tos/index.html -> about-tos.html
	# Add {{ staticCDNHost }} prefix to /static/ paths
	for page in privacy license tos help app; do
		local src_file="$dist_src/$page/index.html"
		if [ -f "$src_file" ]; then
			local template_name="about-${page}.html"
			sed 's|href="/static/|href="{{ staticCDNHost }}/static/|g; s|src="/static/|src="{{ staticCDNHost }}/static/|g' \
				"$src_file" > "$templates/$template_name"
		fi
	done

	# Copy static assets
	if [ -d "$static_src" ]; then
		cp -f "$static_src/"* "$static_out/" 2>/dev/null
	fi

	echo "✅ Generated bskyweb templates"
	echo "   - about-privacy.html, about-tos.html, etc."
	echo ""
}

function ios-setup-reset() {
	echo "Resetting social-app repository..."
	cd $target_dir
	git stash
	git checkout .
	echo "Reset complete"
}

# Main execution
ios-env

case "$1" in
	patch)
		ios-setup-clone
		ios-generate-build-number
		ios-patch-apply-all
		ios-restore-build-placeholder
		ios-copy-new-files
		ios-generate-bskyweb-templates
		show-failed-patches
		exit
		;;
	reset)
		ios-setup-reset
		exit
		;;
	html)
		# Generate bskyweb templates only (requires patches to be applied first)
		ios-generate-bskyweb-templates
		exit
		;;
	*)
		ios-setup-clone
		ios-generate-build-number
		ios-patch-apply-all
		ios-restore-build-placeholder
		ios-copy-new-files
		ios-generate-bskyweb-templates
		show-failed-patches
		;;
esac
