## Test suite for migration tools
## Task 42: Implement migration tools

import unittest, os, strutils, times, sequtils
import ../src/nimpak/migration
import ../src/nimpak/cas

suite "Migration Tools Tests":

  var testDir: string
  var mm: MigrationManager
  
  setup:
    testDir = getTempDir() / "nip_migration_test_" & $epochTime().int
    createDir(testDir)
    mm = initMigrationManager(testDir / "cas", dryRun = true, verbose = false)

  teardown:
    removeDir(testDir)

  test "Migration manager initialization":
    check mm.dryRun == true
    check mm.verbose == false

  test "Legacy NIP migration - missing directory":
    let result = mm.migrateLegacyNip("/nonexistent/path")
    
    check result.success == false
    check result.source == OldNip
    check result.errors.len > 0
    check result.errors[0].contains("not found")

  test "Legacy NIP migration - valid directory":
    # Create a mock legacy NIP structure
    let legacyDir = testDir / "legacy-app"
    createDir(legacyDir)
    createDir(legacyDir / "bin")  # Create bin directory first
    writeFile(legacyDir / "manifest.kdl", "name \"test-app\"\nversion \"1.0.0\"")
    writeFile(legacyDir / "bin" / "app", "#!/bin/sh\necho hello")
    
    let result = mm.migrateLegacyNip(legacyDir)
    
    check result.source == OldNip
    check result.packageName == "legacy-app"
    # In dry-run mode, no actual migration happens
    check result.success == true or result.errors.len == 0

  test "Flatpak migration - not installed":
    let result = mm.migrateFlatpak("org.nonexistent.app")
    
    check result.success == false
    check result.source == Flatpak
    check result.errors.anyIt(it.contains("not found"))

  test "AppImage migration - file not found":
    let result = mm.migrateAppImage("/nonexistent/app.AppImage")
    
    check result.success == false
    check result.source == AppImage
    check result.errors.anyIt(it.contains("not found"))

  test "Docker migration placeholder":
    let result = mm.migrateDockerImage("alpine:latest")
    
    check result.source == Docker
    check result.packageName == "alpine-latest"
    # Placeholder always succeeds
    check result.success == true
    check result.warnings.len > 0

  test "Nix migration - invalid path":
    let result = mm.migrateNixPackage("/invalid/path")
    
    check result.success == false
    check result.source == Nix
    check result.errors.anyIt(it.contains("Invalid Nix store path"))

  test "Format conversion - NPK to NIP":
    let result = mm.convertNpkToNip("/path/to/package.npk")
    
    check result.success == true  # Placeholder
    check result.warnings.len > 0

  test "Format conversion - NIP to NEXTER":
    let result = mm.convertNipToNexter("/path/to/app.nip")
    
    check result.success == true  # Placeholder
    check result.warnings.len > 0

  test "Migration report generation":
    let results = @[
      MigrationResult(success: true, source: OldNip, packageName: "app1", casHashes: @["h1", "h2"], errors: @[], warnings: @[]),
      MigrationResult(success: false, source: Flatpak, packageName: "app2", casHashes: @[], errors: @["Error"], warnings: @[]),
      MigrationResult(success: true, source: Docker, packageName: "app3", casHashes: @["h3"], errors: @[], warnings: @["Warning"])
    ]
    
    let report = generateMigrationReport(results)
    
    check report.contains("Migration Report")
    check report.contains("Total migrations: 3")
    check report.contains("Successful: 2")
    check report.contains("Failed: 1")
    check report.contains("app1")
    check report.contains("app2")
    check report.contains("app3")
    check report.contains("✅")
    check report.contains("❌")

  test "Migration verification - empty result":
    let emptyResult = MigrationResult(
      success: true,
      source: OldNip,
      packageName: "empty",
      casHashes: @[],
      errors: @[]
    )
    
    # Empty migration with no objects should verify
    check mm.verifyMigration(emptyResult) == true

  test "Migration verification - failed result":
    let failedResult = MigrationResult(
      success: false,
      source: OldNip,
      packageName: "failed",
      casHashes: @[],
      errors: @["Something went wrong"]
    )
    
    check mm.verifyMigration(failedResult) == false
