import pytest
import os
import io
import json
from werkzeug.datastructures import FileStorage


class TestDocuments:
    """Test document management functionality."""

    def setup_project(self, logged_in_client, app):
        """Helper to create a test project."""
        # Create a project
        logged_in_client.post(
            "/projects/create",
            data={
                "codigo": "TESTDOC",
                "descripcion": "Proyecto para documentos",
                "cliente": "Cliente Test",
                "esquema": "TEST001",
                "destinacion": "Pruebas",
                "notas": "Proyecto para pruebas de documentos",
            },
            follow_redirects=True,
        )

        # Find the project ID
        with app.app_context():
            projects_dir = os.path.join(app.config["STORAGE_PATH"], "projects")
            project_dirs = [d for d in os.listdir(projects_dir) if "TESTDOC" in d]
            assert len(project_dirs) > 0

            project_dir = project_dirs[0]
            return project_dir.split("_")[0].replace("@", "")

    def test_upload_document(self, logged_in_client, app):
        """Test uploading a document to a project."""
        # Create a project and get its ID
        project_id = self.setup_project(logged_in_client, app)

        # Create a test file
        test_file = FileStorage(
            stream=io.BytesIO(b"This is a test document content."),
            filename="test_document.txt",
            content_type="text/plain",
        )

        # Upload the document
        response = logged_in_client.post(
            f"/projects/{project_id}/documents/upload",
            data={
                "tipo_doc": "Documento de Prueba",  # Match schema type from TEST001
                "descripcion": "Documento de prueba para tests",
                "file": test_file,
            },
            content_type="multipart/form-data",
            follow_redirects=True,
        )

        assert response.status_code == 200

        # Verify document was created
        with app.app_context():
            project_path = None

            projects_dir = os.path.join(app.config["STORAGE_PATH"], "projects")
            for dir_name in os.listdir(projects_dir):
                if dir_name.startswith(f"@{project_id}_"):
                    project_path = os.path.join(projects_dir, dir_name)
                    break

            assert project_path is not None

            # Check for documents directory with content
            docs_path = os.path.join(project_path, "documents")
            assert os.path.exists(docs_path)

            # Should have at least one document folder
            assert len(os.listdir(docs_path)) > 0

    def test_document_versions(self, logged_in_client, app):
        """Test document versioning functionality."""
        # Create a project and upload first version
        project_id = self.setup_project(logged_in_client, app)

        # Upload first version
        test_file1 = FileStorage(
            stream=io.BytesIO(b"Document content version 1"),
            filename="test_versioning.txt",
            content_type="text/plain",
        )

        logged_in_client.post(
            f"/projects/{project_id}/documents/upload",
            data={
                "tipo_doc": "Documento de Prueba",
                "descripcion": "Documento para pruebas de versiones",
                "file": test_file1,
            },
            content_type="multipart/form-data",
            follow_redirects=True,
        )

        # Find the document ID
        doc_id = None
        with app.app_context():
            projects_dir = os.path.join(app.config["STORAGE_PATH"], "projects")
            for dir_name in os.listdir(projects_dir):
                if dir_name.startswith(f"@{project_id}_"):
                    project_path = os.path.join(projects_dir, dir_name)
                    docs_path = os.path.join(project_path, "documents")

                    # Get first document directory
                    doc_dirs = os.listdir(docs_path)
                    if doc_dirs:
                        doc_id = doc_dirs[0].split("_")[0].replace("@", "")
                        break

        assert doc_id is not None

        # Upload second version of the same document
        test_file2 = FileStorage(
            stream=io.BytesIO(b"Document content version 2 - UPDATED"),
            filename="test_versioning_v2.txt",
            content_type="text/plain",
        )

        response = logged_in_client.post(
            f"/projects/{project_id}/documents/{doc_id}/upload",
            data={"descripcion": "Segunda versión del documento", "file": test_file2},
            content_type="multipart/form-data",
            follow_redirects=True,
        )

        assert response.status_code == 200

        # Check for multiple versions in metadata
        with app.app_context():
            projects_dir = os.path.join(app.config["STORAGE_PATH"], "projects")
            for dir_name in os.listdir(projects_dir):
                if dir_name.startswith(f"@{project_id}_"):
                    project_path = os.path.join(projects_dir, dir_name)
                    docs_path = os.path.join(project_path, "documents")

                    # Find document directory
                    for doc_dir in os.listdir(docs_path):
                        if doc_dir.startswith(f"@{doc_id}_"):
                            doc_path = os.path.join(docs_path, doc_dir)
                            meta_path = os.path.join(doc_path, "meta.json")

                            # Check metadata for versions
                            if os.path.exists(meta_path):
                                with open(meta_path, "r") as f:
                                    metadata = json.load(f)
                                    assert "versions" in metadata
                                    assert len(metadata["versions"]) >= 2
