/*
 * Copyright (C) 2023, Dariusz Luksza <dariusz.luksza@gmail.com> and others
 *
 * This program and the accompanying materials are made available under the
 * terms of the Eclipse Distribution License v. 1.0 which is available at
 * https://www.eclipse.org/org/documents/edl-v10.php.
 *
 * SPDX-License-Identifier: BSD-3-Clause
 */
package org.eclipse.jgit.transport;

import static org.junit.Assert.fail;
import static org.eclipse.jgit.lib.Constants.HEAD;
import static org.junit.Assert.assertTrue;
import static org.junit.Assert.assertEquals;

import java.util.Arrays;
import java.util.Collection;
import java.util.Collections;

import org.eclipse.jgit.internal.storage.dfs.DfsRepositoryDescription;
import org.eclipse.jgit.internal.storage.dfs.InMemoryRepository;
import org.eclipse.jgit.internal.storage.file.FileRepository;
import org.eclipse.jgit.internal.storage.file.GC;
import org.eclipse.jgit.internal.storage.file.Pack;
import org.eclipse.jgit.internal.storage.pack.PackExt;
import org.eclipse.jgit.junit.LocalDiskRepositoryTestCase;
import org.eclipse.jgit.junit.TestRepository;
import org.eclipse.jgit.junit.TestRepository.CommitBuilder;
import org.eclipse.jgit.lib.NullProgressMonitor;
import org.eclipse.jgit.lib.Repository;
import org.eclipse.jgit.revwalk.RevCommit;
import org.eclipse.jgit.transport.UploadPack.RequestPolicy;
import org.junit.Before;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.junit.runners.Parameterized;
import org.junit.runners.Parameterized.Parameter;
import org.junit.runners.Parameterized.Parameters;

@RunWith(Parameterized.class)
public class UploadPackHandleDeletedPackFileTest
		extends LocalDiskRepositoryTestCase {

	private FileRepository server;

	private TestRepository<FileRepository> remote;

	private Repository client;

	private RevCommit head;

	@Parameter
	public boolean emptyCommit;

	@Parameters(name="empty commit: {0}")
	public static Collection<Boolean[]> initTestData() {
		return Arrays.asList(
				new Boolean[][] { { Boolean.TRUE }, { Boolean.FALSE } });
	}

	@Before
	@Override
	public void setUp() throws Exception {
		super.setUp();
		server = createBareRepository();
		server.getConfig().setString("protocol", null, "version", "2");

		remote = new TestRepository<>(server);
		client = new InMemoryRepository(new DfsRepositoryDescription("client"));

		setupServerRepo();
		head = server.parseCommit(server.resolve(HEAD));
	}

	@Test
	public void testV2PackFileRemovedDuringUploadPack() throws Exception {
		doRemovePackFileDuringUploadPack(PackExt.PACK);
	}

	@Test
	public void testV2IdxFileRemovedDuringUploadPack() throws Exception {
		doRemovePackFileDuringUploadPack(PackExt.INDEX);
	}

	@Test
	public void testV2BitmapFileRemovedDuringUploadPack() throws Exception {
		doRemovePackFileDuringUploadPack(PackExt.BITMAP_INDEX);
	}

	private void doRemovePackFileDuringUploadPack(PackExt packExt)
			throws Exception {
		Object ctx = new Object();
		TestProtocol testProtocol = new TestProtocol<>(
				(Object req, Repository db) -> {
					UploadPack up = new UploadPack(db);
					up.setRequestPolicy(RequestPolicy.REACHABLE_COMMIT);
					Collection<Pack> packs = server.getObjectDatabase()
							.getPacks();
					assertEquals("single pack expected", 1, packs.size());
					Pack pack = packs.iterator().next();

					try {
						addNewCommit();

						new GC(remote.getRepository()).gc();

						pack.getPackFile().create(packExt).delete();
					} catch (Exception e) {
						fail("GC or pack file removal failed");
					}

					return up;
				}, null);

		URIish uri = testProtocol.register(ctx, server);

		try (Transport tn = testProtocol.open(uri, client, "server")) {
			tn.fetch(NullProgressMonitor.INSTANCE,
					Collections.singletonList(new RefSpec(head.name())));
			assertTrue(client.getObjectDatabase().has(head));
		}
	}

	private void addNewCommit() throws Exception {
		CommitBuilder commit = remote.commit().message("2");
		if (!emptyCommit) {
			commit = commit.add("test2.txt", remote.blob("2"));
		}
		remote.update("master", commit.parent(head).create());
	}

	private void setupServerRepo() throws Exception {
		RevCommit commit0 = remote.commit().message("0")
				.add("test.txt", remote.blob("0"))
				.create();
		remote.update("master", commit0);

		new GC(remote.getRepository()).gc(); // create pack files

		head = remote.commit().message("1").parent(commit0)
				.add("test1.txt", remote.blob("1"))
				.create();
		remote.update("master", head);
	}
}