{"id":21659210,"url":"https://github.com/Trendyol/stove","last_synced_at":"2025-07-17T22:31:33.384Z","repository":{"id":65438860,"uuid":"590452775","full_name":"Trendyol/stove","owner":"Trendyol","description":"Stove: The easiest way of writing e2e/component tests for your JVM back-end API with Kotlin","archived":false,"fork":false,"pushed_at":"2024-10-29T08:22:27.000Z","size":7588,"stargazers_count":165,"open_issues_count":5,"forks_count":12,"subscribers_count":14,"default_branch":"main","last_synced_at":"2024-10-29T09:43:02.794Z","etag":null,"topics":["component-testing","e2e-testing","integration-testing","kotlin","ktor","spring-boot","test","test-automation","testcontainers","testing","testing-framework","testing-tools"],"latest_commit_sha":null,"homepage":"https://trendyol.github.io/stove/","language":"Kotlin","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"apache-2.0","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/Trendyol.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null}},"created_at":"2023-01-18T13:03:34.000Z","updated_at":"2024-10-29T08:22:30.000Z","dependencies_parsed_at":"2023-11-14T08:33:25.743Z","dependency_job_id":"2dcf3eba-474c-4393-a642-eb9bce2312e5","html_url":"https://github.com/Trendyol/stove","commit_stats":null,"previous_names":[],"tags_count":37,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/Trendyol%2Fstove","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/Trendyol%2Fstove/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/Trendyol%2Fstove/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/Trendyol%2Fstove/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/Trendyol","download_url":"https://codeload.github.com/Trendyol/stove/tar.gz/refs/heads/main","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":226305659,"owners_count":17603857,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["component-testing","e2e-testing","integration-testing","kotlin","ktor","spring-boot","test","test-automation","testcontainers","testing","testing-framework","testing-tools"],"created_at":"2024-11-25T09:30:40.186Z","updated_at":"2025-07-17T22:31:33.371Z","avatar_url":"https://github.com/Trendyol.png","language":"Kotlin","funding_links":[],"categories":["\u003ca name=\"Kotlin\"\u003e\u003c/a\u003eKotlin","Kotlin","测试","Testing \u0026 Development"],"sub_categories":["Testing Frameworks"],"readme":"\u003ch1 align=\"center\"\u003eStove\u003c/h1\u003e\n\n\u003cp align=\"center\"\u003e\n  \u0026#10077;Where the infrastructure burns down to pure configurations\u003csub\u003e(ashes)\u003c/sub\u003e\u0026#10078; \n\u003c/p\u003e\n\n![Release](https://img.shields.io/maven-central/v/com.trendyol/stove-testing-e2e?versionPrefix=0\u0026label=latest-release\u0026color=blue) [\u003cimg src=\"https://img.shields.io/badge/dynamic/xml?url=https%3A%2F%2Fcentral.sonatype.com%2Frepository%2Fmaven-snapshots%2Fcom%2Ftrendyol%2Fstove-testing-e2e%2Fmaven-metadata.xml\u0026query=%2F%2Fmetadata%2Fversioning%2Flatest\u0026label=latest-snapshot\u0026color=orange\"/\u003e](https://central.sonatype.com/service/rest/repository/browse/maven-snapshots/com/trendyol/) [![codecov](https://codecov.io/gh/Trendyol/stove/graph/badge.svg?token=HcKBT3chO7)](https://codecov.io/gh/Trendyol/stove) [![OpenSSF Scorecard](https://img.shields.io/ossf-scorecard/github.com/Trendyol/stove?label=openssf%20scorecard\u0026style=flat)](https://scorecard.dev/viewer/?uri=github.com/Trendyol/stove)\n\n\n\u003cp align=\"center\"\u003e\u003cimg src=\"./docs/assets/stove_architecture.svg\" with=\"600\" /\u003e\u003c/p\u003e\n\n# What is Stove?\n\nStove is an end-to-end testing framework that simplifies testing by managing physical dependencies and your\napplication in a unified way.\nWrite infrastructure-agnostic but component-aware tests in Kotlin, regardless of your JVM-based tech stack.\n\n### Key Features\n\n* 🚀 Zero Boilerplate: Write clean, focused tests without infrastructure setup code\n* 🔌 Pluggable Architecture: Easily extend with custom infrastructure components\n* 🐳 Docker-Based: Leverages Testcontainers for reliable, isolated test environments\n* 🌐 Framework Agnostic: Works with Spring, Ktor, Micronaut and other JVM frameworks _(up for grabs)_\n* 🔄 Physical Dependencies: Built-in support for Kafka, Couchbase, PostgreSQL, and more\n* ⚡ Fast Development: On top of the boilerplate free testing, optional Reuse test containers for blazing-fast local\n  development\n\n## Supported Infrastructure\n\nPhysical dependencies:\n\n* ✅ Kafka\n* ✅ Couchbase\n* ✅ PostgreSQL\n* ✅ ElasticSearch\n* ✅ MongoDB\n* ✅ MSSQL\n* ✅ Redis\n* ✅ HTTP Client\n* ✅ WireMock\n\nFrameworks:\n\n* ✅ Spring\n* ✅ Ktor\n* ✅ Micronaut\n* ✅ [Quarkus](https://github.com/Trendyol/stove/tree/main/recipes/java-recipes/quarkus-recipe) (incubating)\n\n## Quick Start\n\nAs of 5th June 2025, Stove's snapshot packages are hosted on [Central Sonatype](https://central.sonatype.com/service/rest/repository/browse/maven-snapshots/com/trendyol/)\n\n```kotlin\nrepositories {\n  maven(\"https://central.sonatype.com/repository/maven-snapshots\")\n}\n```\n\nFor more info about how to use snapshots on the [central sonatype's docs.](https://central.sonatype.org/publish/publish-portal-snapshots/#consuming-snapshot-releases-for-your-project)\n\n### Add the dependency\n\n```kotlin\n// Add the following dependencies to your build.gradle.kts\ntestImplementation(\"com.trendyol:stove-testing-e2e:${version}\")\n\n// And the any of the following for the infrastructure you want to use, for example Kafka\n// you can also use Couchbase, PostgreSQL, ElasticSearch, MongoDB, MSSQL, Redis, HTTP Client, WireMock\n// as much as you want\ntestImplementation(\"com.trendyol:stove-testing-e2e-kafka:${version}\")\n\n// And Application Under Test (AUT)\ntestImplementation(\"com.trendyol:stove-ktor-testing-e2e:${version}\")\n\n// Or\ntestImplementation(\"com.trendyol:stove-spring-testing-e2e:${version}\")\n```\n\n### Set Up the TestSystem\n\n```kotlin\nTestSystem() {\n  if (isRunningLocally()) {\n    enableReuseForTestContainers()\n\n    // this will keep the dependencies running\n    // after the tests are finished,\n    // so next run will be blazing fast :)\n    keepDendenciesRunning()\n  }\n}.with {\n  // Enables http client \n  // to make real http calls \n  // against the application under test\n  httpClient {\n    HttpClientSystemOptions(\n      baseUrl = \"http://localhost:8001\",\n    )\n  }\n\n  // Enables Couchbase physically \n  // and exposes the configuration \n  // to the application under test\n  couchbase {\n    CouchbaseSystemOptions(\n      defaultBucket = \"Stove\",\n      configureExposedConfiguration = { cfg -\u003e listOf(\"couchbase.hosts=${cfg.hostsWithPort}\") },\n    )\n  }\n\n  // Enables Kafka physically \n  // and exposes the configuration \n  // to the application under test\n  kafka {\n    KafkaSystemOptions(\n      configureExposedConfiguration = { cfg -\u003e listOf(\"kafka.bootstrapServers=${cfg.boostrapServers}\") },\n    )\n  }\n\n  // Enables Wiremock on the given port \n  // and provides configurable mock HTTP server \n  // for your external API calls\n  wiremock {\n    WireMockSystemOptions(\n      port = 9090,\n      removeStubAfterRequestMatched = true,\n      afterRequest = { e, _, _ -\u003e\n        logger.info(e.request.toString())\n      },\n    )\n  }\n\n  // The Application Under Test. \n  // Enables Spring Boot application \n  // to be run with the given parameters.\n  springBoot(\n    runner = { parameters -\u003e\n      stove.spring.example.run(parameters) { it.addTestSystemDependencies() }\n    },\n    withParameters = listOf(\n      \"server.port=8001\",\n      \"logging.level.root=warn\",\n      \"logging.level.org.springframework.web=warn\",\n      \"spring.profiles.active=default\",\n      \"kafka.heartbeatInSeconds=2\",\n    ),\n  )\n}.run()\n\n```\n\n### Write Tests\n\n```kotlin\nTestSystem.validate {\n  wiremock {\n    mockGet(\"/example-url\", responseBody = None, statusCode = 200)\n  }\n\n  http {\n    get\u003cString\u003e(\"/hello/index\") { actual -\u003e\n      actual shouldContain \"Hi from Stove framework\"\n      println(actual)\n    }\n  }\n\n  couchbase {\n    shouldQuery\u003cAny\u003e(\"SELECT * FROM system:keyspaces\") { actual -\u003e\n      println(actual)\n    }\n  }\n\n  kafka {\n    shouldBePublished\u003cExampleMessage\u003e {\n      actual.aggregateId == 123\n          \u0026\u0026 metadata.topic = \"example-topic\"\n          \u0026\u0026 metadata.headers[\"example-header\"] == \"example-value\"\n    }\n    shouldBeConsumed\u003cExampleMessage\u003e {\n      actual.aggregateId == 123\n          \u0026\u0026 metadata.topic = \"example-topic\"\n          \u0026\u0026 metadata.headers[\"example-header\"] == \"example-value\"\n    }\n  }\n\n  couchbase {\n    save(collection = \"Backlogs\", id = \"id-of-backlog\", instance = Backlog(\"id-of-backlog\"))\n  }\n\n  http {\n    postAndExpectBodilessResponse(\"/backlog/reserve\") { actual -\u003e\n      actual.status.shouldBe(200)\n    }\n  }\n\n  kafka {\n    shouldBeConsumed\u003cProductCreated\u003e {\n      actual.aggregateId == expectedId\n    }\n  }\n}\n```\n\n## Why Stove?\n\nThe JVM ecosystem lacks a unified approach to end-to-end testing.\nWhile tools like Testcontainers exist, developers still need to:\n\n* Write extensive boilerplate code\n* Complex setup code for each tech stack\n* Create different testing setups for each framework\n* Manage complex infrastructure configurations for each framework\n\nThis affects teams across many tech stacks:\n\n* Kotlin with Spring Boot/Ktor\n* Java with Spring Boot/Micronaut/Quarkus\n* Scala with Spring Boot\n\nStove solves these challenges by providing:\n\n* A unified testing API across all JVM stacks\n* Built-in support for common infrastructure\n* Clean, Kotlin-based test syntax\n* Reusable test containers for fast local development\n\n**Stove unifies the testing experience across all JVM stacks, making it easier to write clean, focused tests.**\n\n## Resources\n\n* 📖 [Documentation](https://trendyol.github.io/stove/)\n* [📹 Youtube Session about how to use](https://youtu.be/DJ0CI5cBanc?t=669) _(Turkish)_\n* 📝 [Motivation Article](https://medium.com/trendyol-tech/a-new-approach-to-the-api-end-to-end-testing-in-kotlin-f743fd1901f5)\n\n## Status\n\n\u003e [!WARNING]\n\u003e While Stove is production-ready and extensively used, the API is not yet fully stabilized. Breaking changes may\n\u003e occur in minor releases, but migration guides will always be provided.\n\n## Contributing\n\nContributions are welcome! Whether it's:\n\n* 🐛 [Bug reports](https://github.com/Trendyol/stove/issues)\n* 💡 [Feature requests](https://github.com/Trendyol/stove/issues)\n* 📖 Documentation improvements\n* 🚀 Code contributions\n\n## License\n\nStove is licensed under the Apache License, Version 2.0. See [LICENSE](LICENSE) for the full license text.\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2FTrendyol%2Fstove","html_url":"https://awesome.ecosyste.ms/projects/github.com%2FTrendyol%2Fstove","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2FTrendyol%2Fstove/lists"}