Skip to content

Commit

Permalink
Adds MenuStack test to showcase parameters backfill.
Browse files Browse the repository at this point in the history
  • Loading branch information
mpawliszyn committed Aug 22, 2024
1 parent 1641dbf commit 2575c9a
Show file tree
Hide file tree
Showing 12 changed files with 196 additions and 6 deletions.
1 change: 1 addition & 0 deletions client-misk-hibernate/build.gradle.kts
Original file line number Diff line number Diff line change
Expand Up @@ -41,6 +41,7 @@ dependencies {
testImplementation(libs.okHttp)

testImplementation(project(":backfila-embedded"))
testImplementation(project(":client-static"))
testImplementation(project(":client-testing"))
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@ import app.cash.backfila.client.misk.hibernate.NullableParameterBackfill
import app.cash.backfila.client.misk.hibernate.RecordNoParametersConfigValuesBackfill
import app.cash.backfila.client.misk.hibernate.SinglePartitionHibernateTestBackfill
import app.cash.backfila.client.misk.hibernate.StringKeyBackfill
import app.cash.backfila.client.misk.menustack.MenuStackModule
import app.cash.backfila.embedded.EmbeddedBackfilaModule
import misk.MiskTestingServiceModule
import misk.environment.DeploymentModule
Expand Down Expand Up @@ -72,5 +73,7 @@ internal class ClientMiskTestingModule(
install(HibernateBackfillModule.create<RecordNoParametersConfigValuesBackfill>())
install(HibernateBackfillModule.create<StringKeyBackfill>())
install(HibernateBackfillModule.create<NullableParameterBackfill>())

install(MenuStackModule())
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,8 @@ class DbMenu() : DbUnsharded<DbMenu> {
constructor(name: String) : this() {
this.name = name
}

fun menuItem() = MenuItem(id, name)
}

interface MenuQuery : Query<DbMenu> {
Expand All @@ -32,3 +34,8 @@ interface MenuQuery : Query<DbMenu> {
@Constraint(path = "id", operator = Operator.EQ)
fun id(id: Id<DbMenu>): MenuQuery
}

data class MenuItem(
val id: Id<DbMenu>,
val name: String,
)
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,7 @@ import misk.hibernate.Id
import misk.hibernate.Query
import misk.hibernate.Transacter
import misk.hibernate.load
import misk.hibernate.newQuery
import misk.testing.MiskTest
import misk.testing.MiskTestModule
import org.assertj.core.api.Assertions.assertThat
Expand Down Expand Up @@ -54,7 +55,7 @@ class ChickenToBeefBackfill @Inject constructor(
) : HibernateBackfill<DbMenu, Id<DbMenu>, NoParameters>() {

override fun backfillCriteria(config: BackfillConfig<NoParameters>): Query<DbMenu> {
return queryFactory.newQuery(MenuQuery::class)
return queryFactory.newQuery<MenuQuery>()
.name("chicken")
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,7 @@ import javax.inject.Inject
import misk.hibernate.Id
import misk.hibernate.Query
import misk.hibernate.Transacter
import misk.hibernate.newQuery
import misk.testing.MiskTest
import misk.testing.MiskTestModule
import org.assertj.core.api.Assertions.assertThat
Expand Down Expand Up @@ -49,7 +50,7 @@ class RecordNoParametersConfigValuesBackfill @Inject constructor(
val configLog = mutableListOf<BackfillConfig<NoParameters>>()

override fun backfillCriteria(config: BackfillConfig<NoParameters>): Query<DbMenu> {
return queryFactory.newQuery(MenuQuery::class)
return queryFactory.newQuery<MenuQuery>()
}

override fun runOne(pkey: Id<DbMenu>, config: BackfillConfig<NoParameters>) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,7 @@ import javax.inject.Inject
import misk.hibernate.Id
import misk.hibernate.Query
import misk.hibernate.Transacter
import misk.hibernate.newQuery
import misk.testing.MiskTest
import misk.testing.MiskTestModule
import org.assertj.core.api.Assertions.assertThat
Expand Down Expand Up @@ -72,7 +73,7 @@ class NullableParameterBackfill @Inject constructor(
val parameters = mutableListOf<Parameters>()

override fun backfillCriteria(config: BackfillConfig<Parameters>): Query<DbMenu> {
return queryFactory.newQuery(MenuQuery::class)
return queryFactory.newQuery<MenuQuery>()
}

override fun runOne(pkey: Id<DbMenu>, config: BackfillConfig<Parameters>) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@ import javax.inject.Inject
import misk.hibernate.Id
import misk.hibernate.Query
import misk.hibernate.Transacter
import misk.hibernate.newQuery

@Description("So we can backfill menus.")
class SinglePartitionHibernateTestBackfill @Inject constructor(
Expand All @@ -20,7 +21,7 @@ class SinglePartitionHibernateTestBackfill @Inject constructor(
val parametersLog = mutableListOf<SandwichParameters>()

override fun backfillCriteria(config: BackfillConfig<SandwichParameters>): Query<DbMenu> {
return queryFactory.newQuery(MenuQuery::class).name(config.parameters.type ?: "beef")
return queryFactory.newQuery<MenuQuery>().name(config.parameters.type ?: "beef")
}

override fun runBatch(pkeys: List<Id<DbMenu>>, config: BackfillConfig<SandwichParameters>) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,7 @@ import com.google.inject.Module
import javax.inject.Inject
import misk.hibernate.Query
import misk.hibernate.Transacter
import misk.hibernate.newQuery
import misk.testing.MiskTest
import misk.testing.MiskTestModule
import org.assertj.core.api.Assertions.assertThat
Expand Down Expand Up @@ -73,7 +74,7 @@ class StringKeyBackfill @Inject constructor(
}

override fun backfillCriteria(config: BackfillConfig<NoParameters>): Query<DbMenu> {
return queryFactory.newQuery(MenuQuery::class)
return queryFactory.newQuery<MenuQuery>()
}

override fun runOne(pkey: String, config: BackfillConfig<NoParameters>) {
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,80 @@
package app.cash.backfila.client.misk.menustack

import app.cash.backfila.client.BackfillConfig
import app.cash.backfila.client.misk.ClientMiskService
import app.cash.backfila.client.misk.DbMenu
import app.cash.backfila.client.misk.MenuItem
import app.cash.backfila.client.misk.MenuQuery
import app.cash.backfila.client.misk.hibernate.HibernateBackfill
import app.cash.backfila.client.misk.hibernate.UnshardedPartitionProvider
import app.cash.backfila.client.stat.parameters.DatasourceParameters
import app.cash.backfila.client.stat.parameters.ParametersDatasourceBackfill
import java.util.concurrent.BlockingDeque
import javax.inject.Inject
import misk.hibernate.Id
import misk.hibernate.Query
import misk.hibernate.Transacter
import misk.hibernate.newQuery

/**
* Backfills all menus of a specific type to the singleton menuStack.
*/
class MenuStackDbBackfill @Inject constructor(
@ClientMiskService private val transacter: Transacter,
private val queryFactory: Query.Factory,
private val menuProcessor: MenuProcessor,
) : HibernateBackfill<DbMenu, Id<DbMenu>, MenuStackDbParameters>() {
override fun backfillCriteria(config: BackfillConfig<MenuStackDbParameters>): Query<DbMenu> {
return queryFactory.newQuery<MenuQuery>().name(config.parameters.type)
}

override fun runOne(pkey: Id<DbMenu>, config: BackfillConfig<MenuStackDbParameters>) {
menuProcessor.addToStack(pkey, config)
}

override fun partitionProvider() = UnshardedPartitionProvider(transacter)
}

/**
* Backfills all menus specified by ID in the backfill parameters to the singleton menuStack.
*/
class MenuStackParametersBackfill @Inject constructor(
private val menuProcessor: MenuProcessor,
) : ParametersDatasourceBackfill<Id<DbMenu>, MenuStackIdParameters>() {
override fun runOne(item: Id<DbMenu>, config: BackfillConfig<MenuStackIdParameters>) {
menuProcessor.addToStack(item, config)
}
}

/**
* Processes a menu and places it onto the menuStack.
*/
class MenuProcessor @Inject constructor(
@ClientMiskService private val transacter: Transacter,
private val queryFactory: Query.Factory,
@MenuStack private val menuStack: BlockingDeque<MenuItem>,
) {
fun addToStack(item: Id<DbMenu>, config: BackfillConfig<*>) {
val menuItem = transacter.transaction { session ->
queryFactory.newQuery<MenuQuery>().id(item).list(session).single().menuItem()
}
if (!config.dryRun) {
menuStack.add(menuItem)
}
}
}

data class MenuStackDbParameters(
/**
* beef, chicken, duck ....
*/
val type: String,
)

data class MenuStackIdParameters(
val menuIds: String,
) : DatasourceParameters<Id<DbMenu>> {
override fun getBackfillData(): List<Id<DbMenu>> {
return menuIds.split(',').map { Id(it.toLong()) }
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
package app.cash.backfila.client.misk.menustack

import app.cash.backfila.client.misk.MenuItem
import app.cash.backfila.client.misk.hibernate.HibernateBackfillModule
import app.cash.backfila.client.stat.StaticDatasourceBackfillModule
import com.google.inject.Provides
import java.util.concurrent.BlockingDeque
import java.util.concurrent.LinkedBlockingDeque
import javax.inject.Singleton
import misk.inject.KAbstractModule

class MenuStackModule : KAbstractModule() {
override fun configure() {
install(HibernateBackfillModule.create<MenuStackDbBackfill>())
install(StaticDatasourceBackfillModule.create<MenuStackParametersBackfill>())
}

@Provides @MenuStack @Singleton
fun provideMenuStack(): BlockingDeque<MenuItem> = LinkedBlockingDeque()
}

annotation class MenuStack
Original file line number Diff line number Diff line change
@@ -0,0 +1,71 @@
package app.cash.backfila.client.misk.menustack

import app.cash.backfila.client.misk.ClientMiskService
import app.cash.backfila.client.misk.ClientMiskTestingModule
import app.cash.backfila.client.misk.DbMenu
import app.cash.backfila.client.misk.MenuItem
import app.cash.backfila.client.misk.MenuQuery
import app.cash.backfila.embedded.Backfila
import app.cash.backfila.embedded.createDryRun
import app.cash.backfila.embedded.createWetRun
import com.google.inject.Module
import java.util.concurrent.BlockingDeque
import javax.inject.Inject
import misk.hibernate.Query
import misk.hibernate.Session
import misk.hibernate.Transacter
import misk.hibernate.newQuery
import misk.testing.MiskTest
import misk.testing.MiskTestModule
import org.assertj.core.api.Assertions.assertThat
import org.junit.jupiter.api.Test

@MiskTest(startService = true)
class MenuStackTest {
@Suppress("unused")
@MiskTestModule
val module: Module = ClientMiskTestingModule(false)

@Inject @ClientMiskService
lateinit var transacter: Transacter

@Inject lateinit var queryFactory: Query.Factory

@Inject lateinit var backfila: Backfila

@MenuStack @Inject
lateinit var menuStack: BlockingDeque<MenuItem>

/**
* This test helps give customers of Backfila some idea on how different backfills built on different clients
* that perform the same underlying action can be used together.
*
* Gives customers an alternative to adding `in` clauses to their DB backfills that perform poorly.
*/
@Test
fun `shows how using a hibernate backfill and a parameter backfill a common stack of menus can be created`() {
// Fill the database with chicken, beef and duck.
transacter.transaction { session: Session ->
repeat(10) { session.save(DbMenu("chicken")) }
repeat(5) { session.save(DbMenu("beef")) }
repeat(8) { session.save(DbMenu("duck")) }
repeat(10) { session.save(DbMenu("chicken")) }
}

// Dry run all the beef.
backfila.createDryRun<MenuStackDbBackfill>(parameters = MenuStackDbParameters(type = "beef")).execute()

// Wet run all the chicken.
backfila.createWetRun<MenuStackDbBackfill>(parameters = MenuStackDbParameters(type = "chicken")).execute()

// Pick 4 duck menu ids and backfill those using a comma separated parameter.
val pickedString = transacter.transaction { session: Session ->
queryFactory.newQuery<MenuQuery>().name("duck").list(session).map { it.id }.take(4).joinToString(separator = ",")
}
backfila.createWetRun<MenuStackParametersBackfill>(parameters = MenuStackIdParameters(menuIds = pickedString)).execute()

// Check that the singleton stack of menus is exactly 20 chicken followed by 4 duck.
val expected = List(20) { "chicken" } + List(4) { "duck" }
assertThat(menuStack.map { it.name }).containsExactlyElementsOf(expected.toList())
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,7 @@ import misk.hibernate.Id
import misk.hibernate.Query
import misk.hibernate.Transacter
import misk.hibernate.load
import misk.hibernate.newQuery
import wisp.logging.getLogger

internal class BackfillRegisteredParameters @Inject constructor(
Expand Down Expand Up @@ -41,7 +42,7 @@ internal class BackfillRegisteredParameters @Inject constructor(
override fun partitionProvider(): PartitionProvider = UnshardedPartitionProvider(transacter)

override fun backfillCriteria(config: BackfillConfig<NoParameters>): Query<DbRegisteredBackfill> {
return queryFactory.newQuery(RegisteredBackfillQuery::class)
return queryFactory.newQuery<RegisteredBackfillQuery>()
}

companion object {
Expand Down

0 comments on commit 2575c9a

Please sign in to comment.