# frozen_string_literal: true

require 'test_helper'
require 'zip'

class ZipDownloadJobTest < ActiveJob::TestCase
  test 'creates a zip file' do
    album = create(:album)
    track1 = create(:track, album:, title: 'First Track', position: 1)
    track2 = create(:track, album:, title: 'Second Track', position: 2)
    create(:transcode, track: track1, format: :mp3v0)
    create(:transcode, track: track2, format: :mp3v0)
    purchase = create(:purchase, price: album.price, album:)

    ZipDownloadJob.perform_now(purchase)

    assert_equal 1, purchase.purchase_downloads.count

    entries = []
    purchase.purchase_downloads.last.file.open do |zip_file|
      Zip::File.open(zip_file) do |zip|
        zip.each do |entry|
          entries << entry.name
        end
      end
    end

    assert entries.include? '01 - First Track.mp3'
    assert entries.include? '02 - Second Track.mp3'
  end

  test 'replaces existing zip file' do
    album = create(:album)
    track = create(:track, album:)
    create(:transcode, track:, format: :mp3v0)
    purchase = create(:purchase, price: album.price, album:)
    create(:purchase_download, purchase:, format: :mp3v0)

    assert_equal 1, purchase.purchase_downloads.count
    ZipDownloadJob.perform_now(purchase)
    assert_equal 1, purchase.reload.purchase_downloads.count
  end

  test 'creates a zip file when the album title contains a /' do
    album = create(:album, title: 'Slash / Slash')
    track = create(:track, album:, title: 'First / Track', position: 1)
    create(:transcode, track:, format: :mp3v0)
    purchase = create(:purchase, price: album.price, album:)

    ZipDownloadJob.perform_now(purchase)

    assert_equal 1, purchase.purchase_downloads.count

    entries = []
    purchase.purchase_downloads.last.file.open do |zip_file|
      Zip::File.open(zip_file) do |zip|
        zip.each do |entry|
          entries << entry.name
        end
      end
    end

    assert entries.include? '01 - First Track.mp3'
  end

  test 'uses /var/data for tmp files when that path exists' do
    Dir.stubs(:exist?).with('/var/data').returns(true)
    Dir.expects(:mktmpdir).with(nil, '/var/data')

    ZipDownloadJob.perform_now(build(:purchase))
  end

  test 'uses default for tmp files when /var/data does not exist' do
    Dir.stubs(:exist?).with('/var/data').returns(false)
    Dir.expects(:mktmpdir).with(nil, nil)

    ZipDownloadJob.perform_now(build(:purchase))
  end
end
