"""Tests for SchemaBuilder."""

from pinecone import SchemaBuilder


def test_schema_builder_empty():
    """Test empty schema builder."""
    schema = SchemaBuilder().build()
    assert schema == {"fields": {}}


def test_schema_builder_dense_vector_field():
    """Test adding dense vector field."""
    schema = (
        SchemaBuilder().add_dense_vector_field("embedding", dimension=768, metric="cosine").build()
    )

    assert schema == {
        "fields": {
            "embedding": {
                "type": "dense_vector",
                "dimension": 768,
                "metric": "cosine",
            }
        }
    }


def test_schema_builder_dense_vector_field_with_description():
    """Test adding dense vector field with description."""
    schema = (
        SchemaBuilder()
        .add_dense_vector_field(
            "embedding",
            dimension=1536,
            metric="euclidean",
            description="OpenAI embeddings",
        )
        .build()
    )

    assert schema == {
        "fields": {
            "embedding": {
                "type": "dense_vector",
                "dimension": 1536,
                "metric": "euclidean",
                "description": "OpenAI embeddings",
            }
        }
    }


def test_schema_builder_string_field_filterable():
    """Test adding filterable string field."""
    schema = SchemaBuilder().add_string_field("category", filterable=True).build()

    assert schema == {
        "fields": {
            "category": {
                "type": "string",
                "full_text_searchable": False,
                "filterable": True,
            }
        }
    }


def test_schema_builder_string_field_full_text_searchable():
    """Test adding full-text searchable string field."""
    schema = (
        SchemaBuilder()
        .add_string_field(
            "title",
            full_text_searchable=True,
            language="en",
            stemming=True,
            lowercase=True,
            max_term_len=100,
        )
        .build()
    )

    assert schema == {
        "fields": {
            "title": {
                "type": "string",
                "full_text_searchable": True,
                "filterable": False,
                "language": "en",
                "stemming": True,
                "lowercase": True,
                "max_term_len": 100,
            }
        }
    }


def test_schema_builder_integer_field():
    """Test adding integer field."""
    schema = (
        SchemaBuilder()
        .add_integer_field("year", filterable=True, description="Publication year")
        .build()
    )

    assert schema == {
        "fields": {
            "year": {
                "type": "integer",
                "filterable": True,
                "description": "Publication year",
            }
        }
    }


def test_schema_builder_sparse_vector_field():
    """Test adding sparse vector field."""
    schema = (
        SchemaBuilder()
        .add_sparse_vector_field("sparse", metric="dotproduct", description="BM25")
        .build()
    )

    assert schema == {
        "fields": {
            "sparse": {
                "type": "sparse_vector",
                "metric": "dotproduct",
                "description": "BM25",
            }
        }
    }


def test_schema_builder_semantic_text_field():
    """Test adding semantic text field."""
    schema = (
        SchemaBuilder()
        .add_semantic_text_field(
            "content",
            model="multilingual-e5-large",
            metric="cosine",
            read_parameters={"input_type": "query"},
            write_parameters={"input_type": "passage"},
        )
        .build()
    )

    assert schema == {
        "fields": {
            "content": {
                "type": "semantic_text",
                "model": "multilingual-e5-large",
                "metric": "cosine",
                "read_parameters": {"input_type": "query"},
                "write_parameters": {"input_type": "passage"},
            }
        }
    }


def test_schema_builder_multiple_fields():
    """Test adding multiple fields."""
    schema = (
        SchemaBuilder()
        .add_dense_vector_field("embedding", dimension=768, metric="cosine")
        .add_string_field("title", full_text_searchable=True, language="en")
        .add_string_field("category", filterable=True)
        .add_integer_field("year", filterable=True)
        .build()
    )

    assert schema == {
        "fields": {
            "embedding": {
                "type": "dense_vector",
                "dimension": 768,
                "metric": "cosine",
            },
            "title": {
                "type": "string",
                "full_text_searchable": True,
                "filterable": False,
                "language": "en",
            },
            "category": {
                "type": "string",
                "full_text_searchable": False,
                "filterable": True,
            },
            "year": {
                "type": "integer",
                "filterable": True,
            },
        }
    }


def test_schema_builder_method_chaining():
    """Test method chaining returns self."""
    builder = SchemaBuilder()
    result = builder.add_string_field("test")

    assert result is builder


def test_schema_builder_field_overwrite():
    """Test that adding same field name twice overwrites."""
    schema = (
        SchemaBuilder()
        .add_string_field("title", filterable=True)
        .add_string_field("title", full_text_searchable=True, language="en")
        .build()
    )

    assert schema == {
        "fields": {
            "title": {
                "type": "string",
                "full_text_searchable": True,
                "filterable": False,
                "language": "en",
            }
        }
    }


def test_schema_builder_additional_options():
    """Test that additional_options are passed through."""
    schema = (
        SchemaBuilder()
        .add_string_field(
            "title",
            full_text_searchable=True,
            case_sensitive=True,  # Future parameter
            experimental_option="value",  # Another future parameter
        )
        .build()
    )

    assert schema == {
        "fields": {
            "title": {
                "type": "string",
                "full_text_searchable": True,
                "filterable": False,
                "case_sensitive": True,
                "experimental_option": "value",
            }
        }
    }


def test_schema_builder_add_custom_field():
    """Test adding custom field definition."""
    schema = (
        SchemaBuilder()
        .add_custom_field(
            "custom",
            {
                "type": "string",
                "experimental_option": True,
                "another_option": "value",
            },
        )
        .build()
    )

    assert schema == {
        "fields": {
            "custom": {
                "type": "string",
                "experimental_option": True,
                "another_option": "value",
            }
        }
    }


def test_schema_builder_post_build_mutation():
    """Test that returned dict can be mutated after build."""
    schema = SchemaBuilder().add_string_field("title").build()

    # Mutate the returned dict
    schema["fields"]["title"]["description"] = "Added after build"
    schema["fields"]["new_field"] = {"type": "integer"}

    assert schema == {
        "fields": {
            "title": {
                "type": "string",
                "full_text_searchable": False,
                "filterable": False,
                "description": "Added after build",
            },
            "new_field": {"type": "integer"},
        }
    }


def test_schema_builder_import_from_top_level():
    """Test that SchemaBuilder can be imported from pinecone."""
    from pinecone import SchemaBuilder as TopLevelSchemaBuilder

    assert TopLevelSchemaBuilder is SchemaBuilder


def test_schema_builder_import_from_models_indexes():
    """Test that SchemaBuilder can be imported from pinecone.models.indexes."""
    from pinecone.models.indexes import SchemaBuilder as ModelsSchemaBuilder

    assert ModelsSchemaBuilder is SchemaBuilder
