Skip to content

Commit

Permalink
Merge pull request #592 from NDLANO/learningpath-seqno-bug
Browse files Browse the repository at this point in the history
learningpath-api: Fix seqNo bug
  • Loading branch information
jnatten authored Feb 3, 2025
2 parents 9540506 + a7ebb88 commit cb84e1a
Show file tree
Hide file tree
Showing 22 changed files with 364 additions and 262 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -49,7 +49,7 @@ class ArticleSearchConverterServiceTest extends UnitSuite with TestEnvironment {
Tag(Seq("the", "words"), "und")
)

override def beforeAll(): Unit = {}
override def beforeAll(): Unit = super.beforeAll()

test("That asSearchableArticle converts titles with correct language") {
val article = TestData.sampleArticleWithByNcSa.copy(title = titles)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -232,6 +232,7 @@ class ArticleSearchServiceTest
)

override def beforeAll(): Unit = if (elasticSearchContainer.isSuccess) {
super.beforeAll()
articleIndexService.createIndexAndAlias().get

articleIndexService.indexDocument(article1).get
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -81,7 +81,7 @@ class SearchConverterServiceTest extends UnitSuite with TestEnvironment {
None
)

override def beforeAll(): Unit = {}
override def beforeAll(): Unit = {super.beforeAll()}

test("That asSearchableAudioInformation converts titles with correct language") {
val searchableAudio = searchConverterService.asSearchableAudioInformation(sampleAudio)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -212,26 +212,29 @@ class PublishedConceptSearchServiceTest
aggregatePaths = List.empty
)

override def beforeAll(): Unit = if (elasticSearchContainer.isSuccess) {
when(taxonomyApiClient.getSubjects).thenReturn(Success(TaxonomyData.empty))
publishedConceptIndexService.createIndexWithName(props.DraftConceptSearchIndex)

publishedConceptIndexService.indexDocument(concept1)
publishedConceptIndexService.indexDocument(concept2)
publishedConceptIndexService.indexDocument(concept3)
publishedConceptIndexService.indexDocument(concept4)
publishedConceptIndexService.indexDocument(concept5)
publishedConceptIndexService.indexDocument(concept6)
publishedConceptIndexService.indexDocument(concept7)
publishedConceptIndexService.indexDocument(concept8)
publishedConceptIndexService.indexDocument(concept9)
publishedConceptIndexService.indexDocument(concept10)
publishedConceptIndexService.indexDocument(concept11)
publishedConceptIndexService.indexDocument(concept12)

blockUntil(() => {
publishedConceptSearchService.countDocuments == 12
})
override def beforeAll(): Unit = {
super.beforeAll()
if (elasticSearchContainer.isSuccess) {
when(taxonomyApiClient.getSubjects).thenReturn(Success(TaxonomyData.empty))
publishedConceptIndexService.createIndexWithName(props.DraftConceptSearchIndex)

publishedConceptIndexService.indexDocument(concept1)
publishedConceptIndexService.indexDocument(concept2)
publishedConceptIndexService.indexDocument(concept3)
publishedConceptIndexService.indexDocument(concept4)
publishedConceptIndexService.indexDocument(concept5)
publishedConceptIndexService.indexDocument(concept6)
publishedConceptIndexService.indexDocument(concept7)
publishedConceptIndexService.indexDocument(concept8)
publishedConceptIndexService.indexDocument(concept9)
publishedConceptIndexService.indexDocument(concept10)
publishedConceptIndexService.indexDocument(concept11)
publishedConceptIndexService.indexDocument(concept12)

blockUntil(() => {
publishedConceptSearchService.countDocuments == 12
})
}
}

test("That getStartAtAndNumResults returns SEARCH_MAX_PAGE_SIZE for value greater than SEARCH_MAX_PAGE_SIZE") {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -208,22 +208,25 @@ class ArticleSearchServiceTest extends IntegrationSuite(EnableElasticsearchConta
articleType = ArticleType.TopicArticle
)

override def beforeAll(): Unit = if (elasticSearchContainer.isSuccess) {
articleIndexService.createIndexAndAlias().get

articleIndexService.indexDocument(article1).get
articleIndexService.indexDocument(article2).get
articleIndexService.indexDocument(article3).get
articleIndexService.indexDocument(article4).get
articleIndexService.indexDocument(article5).get
articleIndexService.indexDocument(article6).get
articleIndexService.indexDocument(article7).get
articleIndexService.indexDocument(article8).get
articleIndexService.indexDocument(article9).get
articleIndexService.indexDocument(article10).get
articleIndexService.indexDocument(article11).get

blockUntil(() => articleSearchService.countDocuments == 11)
override def beforeAll(): Unit = {
super.beforeAll()
if (elasticSearchContainer.isSuccess) {
articleIndexService.createIndexAndAlias().get

articleIndexService.indexDocument(article1).get
articleIndexService.indexDocument(article2).get
articleIndexService.indexDocument(article3).get
articleIndexService.indexDocument(article4).get
articleIndexService.indexDocument(article5).get
articleIndexService.indexDocument(article6).get
articleIndexService.indexDocument(article7).get
articleIndexService.indexDocument(article8).get
articleIndexService.indexDocument(article9).get
articleIndexService.indexDocument(article10).get
articleIndexService.indexDocument(article11).get

blockUntil(() => articleSearchService.countDocuments == 11)
}
}

test("That getStartAtAndNumResults returns SEARCH_MAX_PAGE_SIZE for value greater than SEARCH_MAX_PAGE_SIZE") {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -42,14 +42,17 @@ class GrepCodesSearchServiceTest extends IntegrationSuite(EnableElasticsearchCon

val articlesToIndex: Seq[Draft] = Seq(article1, article2, article3, article4)

override def beforeAll(): Unit = if (elasticSearchContainer.isSuccess) {
tagIndexService.createIndexWithName(props.DraftGrepCodesSearchIndex)
override def beforeAll(): Unit = {
super.beforeAll()
if (elasticSearchContainer.isSuccess) {
tagIndexService.createIndexWithName(props.DraftGrepCodesSearchIndex)

articlesToIndex.foreach(a => grepCodesIndexService.indexDocument(a))
articlesToIndex.foreach(a => grepCodesIndexService.indexDocument(a))

val allGrepCodesToIndex = articlesToIndex.flatMap(_.grepCodes)
val allGrepCodesToIndex = articlesToIndex.flatMap(_.grepCodes)

blockUntil(() => grepCodesSearchService.countDocuments == allGrepCodesToIndex.size)
blockUntil(() => grepCodesSearchService.countDocuments == allGrepCodesToIndex.size)
}
}

test("That searching for grepcodes returns sensible results") {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -67,16 +67,19 @@ class TagSearchServiceTest extends IntegrationSuite(EnableElasticsearchContainer

val articlesToIndex: Seq[Draft] = Seq(article1, article2, article3, article4)

override def beforeAll(): Unit = if (elasticSearchContainer.isSuccess) {
tagIndexService.createIndexAndAlias().get
override def beforeAll(): Unit = {
super.beforeAll()
if (elasticSearchContainer.isSuccess) {
tagIndexService.createIndexAndAlias().get

articlesToIndex.foreach(a => tagIndexService.indexDocument(a).get)
articlesToIndex.foreach(a => tagIndexService.indexDocument(a).get)

val allTagsToIndex = articlesToIndex.flatMap(_.tags)
val groupedByLanguage = allTagsToIndex.groupBy(_.language)
val tagsDistinctByLanguage = groupedByLanguage.values.flatMap(x => x.flatMap(_.tags).toSet)
val allTagsToIndex = articlesToIndex.flatMap(_.tags)
val groupedByLanguage = allTagsToIndex.groupBy(_.language)
val tagsDistinctByLanguage = groupedByLanguage.values.flatMap(x => x.flatMap(_.tags).toSet)

blockUntil(() => tagSearchService.countDocuments == tagsDistinctByLanguage.size)
blockUntil(() => tagSearchService.countDocuments == tagsDistinctByLanguage.size)
}
}

test("That searching for tags returns sensible results") {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -75,15 +75,18 @@ class TagSearchServiceTest

val imagesToIndex: Seq[ImageMetaInformation] = Seq(image1, image2, image3, image4)

override def beforeAll(): Unit = if (elasticSearchContainer.isSuccess) {
tagIndexService.createIndexAndAlias().get
imagesToIndex.foreach(a => tagIndexService.indexDocument(a).get)

val allTagsToIndex = imagesToIndex.flatMap(_.tags)
val groupedByLanguage = allTagsToIndex.groupBy(_.language)
val tagsDistinctByLanguage = groupedByLanguage.values.flatMap(x => x.flatMap(_.tags).toSet)

blockUntil(() => tagSearchService.countDocuments() == tagsDistinctByLanguage.size)
override def beforeAll(): Unit = {
super.beforeAll()
if (elasticSearchContainer.isSuccess) {
tagIndexService.createIndexAndAlias().get
imagesToIndex.foreach(a => tagIndexService.indexDocument(a).get)

val allTagsToIndex = imagesToIndex.flatMap(_.tags)
val groupedByLanguage = allTagsToIndex.groupBy(_.language)
val tagsDistinctByLanguage = groupedByLanguage.values.flatMap(x => x.flatMap(_.tags).toSet)

blockUntil(() => tagSearchService.countDocuments() == tagsDistinctByLanguage.size)
}
}

test("That searching for tags returns sensible results") {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -57,6 +57,7 @@ class ArticleApiClientTest
val articleApiBaseUrl: String = s"http://localhost:$articleApiPort"

override def beforeAll(): Unit = {
super.beforeAll()
implicit val ec: ExecutionContextExecutorService =
ExecutionContext.fromExecutorService(Executors.newSingleThreadExecutor)
articleApi = new articleapi.MainClass(articleApiProperties)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -48,6 +48,7 @@ class ArticleApiClientTest
val articleApiBaseUrl: String = s"http://localhost:$articleApiPort"

override def beforeAll(): Unit = {
super.beforeAll()
implicit val ec: ExecutionContextExecutorService =
ExecutionContext.fromExecutorService(Executors.newSingleThreadExecutor)
articleApi = new articleapi.MainClass(articleApiProperties)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -49,6 +49,7 @@ class DraftApiClientTest
val draftApiBaseUrl: String = s"http://localhost:$draftApiPort"

override def beforeAll(): Unit = {
super.beforeAll()
when(myndlaApiClient.getStatsFor(any, any)).thenReturn(Success(List.empty))
implicit val ec: ExecutionContextExecutorService =
ExecutionContext.fromExecutorService(Executors.newSingleThreadExecutor)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -50,6 +50,7 @@ class LearningpathApiClientTest
val learningpathApiBaseUrl: String = s"http://localhost:$learningpathApiPort"

override def beforeAll(): Unit = {
super.beforeAll()
when(myndlaApiClient.getStatsFor(any, any)).thenReturn(Success(List.empty))
implicit val ec: ExecutionContextExecutorService =
ExecutionContext.fromExecutorService(Executors.newSingleThreadExecutor)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -40,7 +40,7 @@ import no.ndla.learningpathapi.validation.{
UrlValidator
}
import no.ndla.network.NdlaClient
import no.ndla.network.clients.{FeideApiClient, MyNDLAApiClient, RedisClient}
import no.ndla.network.clients.MyNDLAApiClient
import no.ndla.network.tapir.TapirApplication
import no.ndla.search.{BaseIndexService, Elastic4sClient}

Expand All @@ -60,7 +60,6 @@ class ComponentRegistry(properties: LearningpathApiProperties)
with TaxonomyApiClient
with NdlaClient
with ConverterService
with FeideApiClient
with OembedProxyClient
with Elastic4sClient
with DataSource
Expand All @@ -76,7 +75,6 @@ class ComponentRegistry(properties: LearningpathApiProperties)
with TextValidator
with UrlValidator
with ErrorHandling
with RedisClient
with SwaggerDocControllerConfig {
override val props: LearningpathApiProperties = properties
override val migrator: DBMigrator = DBMigrator(
Expand All @@ -100,15 +98,13 @@ class ComponentRegistry(properties: LearningpathApiProperties)
lazy val clock = new SystemClock
lazy val taxonomyApiClient = new TaxonomyApiClient
lazy val ndlaClient = new NdlaClient
lazy val feideApiClient = new FeideApiClient
lazy val languageValidator = new LanguageValidator
lazy val titleValidator = new TitleValidator
lazy val learningPathValidator = new LearningPathValidator
lazy val learningStepValidator = new LearningStepValidator
var e4sClient: NdlaE4sClient = Elastic4sClientFactory.getClient(props.SearchServer)
lazy val searchApiClient = new SearchApiClient
lazy val oembedProxyClient = new OembedProxyClient
lazy val redisClient = new RedisClient(props.RedisHost, props.RedisPort)
lazy val myndlaApiClient = new MyNDLAApiClient

lazy val learningpathControllerV2 = new LearningpathControllerV2
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -20,14 +20,11 @@ trait Props extends HasBaseProps with HasDatabaseProps {
}

class LearningpathApiProperties extends BaseProps with DatabaseProps with StrictLogging {
def IsKubernetes: Boolean = propOrNone("NDLA_IS_KUBERNETES").isDefined

def ApplicationName = "learningpath-api"
def Auth0LoginEndpoint: String = s"https://${AuthUser.getAuth0HostForEnv(Environment)}/authorize"

def ApplicationPort: Int = propOrElse("APPLICATION_PORT", "80").toInt
def DefaultLanguage: String = propOrElse("DEFAULT_LANGUAGE", "nb")
def MaxFolderDepth: Long = propOrElse("MAX_FOLDER_DEPTH", "5").toLong

def Domain: String = propOrElse("BACKEND_API_DOMAIN", Domains.get(Environment))

Expand All @@ -37,12 +34,6 @@ class LearningpathApiProperties extends BaseProps with DatabaseProps with Strict
def MaxPageSize = 10000
def IndexBulkSize = 1000

def InternalImageApiUrl: String = s"$ImageApiHost/image-api/v3/images"
def InternalImageApiRawUrl: String = s"$ImageApiHost/image-api/raw"

def RedisHost: String = propOrElse("REDIS_HOST", "redis")
def RedisPort: Int = propOrElse("REDIS_PORT", "6379").toInt

object ExternalApiUrls {
def ImageApiUrl = s"$Domain/image-api/v3/images"
def ImageApiRawUrl = s"$Domain/image-api/raw"
Expand Down Expand Up @@ -83,8 +74,6 @@ class LearningpathApiProperties extends BaseProps with DatabaseProps with Strict
EnvironmentUrls("test") ++
EnvironmentUrls("staging")

def UsernameHeader = "X-Consumer-Username"

def ElasticSearchIndexMaxResultWindow = 10000
def ElasticSearchScrollKeepAlive = "1m"
def InitialScrollContextKeywords: List[String] = List("0", "initial", "start", "first")
Expand Down Expand Up @@ -117,9 +106,6 @@ class LearningpathApiProperties extends BaseProps with DatabaseProps with Strict
def SearchServer: String =
propOrElse("SEARCH_SERVER", "http://search-learningpath-api.ndla-local")

def RunWithSignedSearchRequests: Boolean =
propOrElse("RUN_WITH_SIGNED_SEARCH_REQUESTS", "true").toBoolean

override def MetaMigrationLocation: String = "no/ndla/learningpathapi/db/migration"
override def MetaMigrationTable: Option[String] = Some("schema_version")
}
Original file line number Diff line number Diff line change
Expand Up @@ -250,6 +250,12 @@ trait LearningPathRepositoryComponent extends StrictLogging {
sql"delete from learningsteps where id = $learningStepId".update()
}

def deleteAllPathsAndSteps(implicit session: DBSession): Try[Unit] =
for {
_ <- Try(sql"delete from learningsteps".update())
_ <- Try(sql"delete from learningpaths".update())
} yield ()

def learningPathsWithIdBetween(min: Long, max: Long)(implicit
session: DBSession = ReadOnlyAutoSession
): List[LearningPath] = {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -19,14 +19,14 @@ import no.ndla.learningpathapi.model.domain.ImplicitLearningPath.ImplicitLearnin
import no.ndla.learningpathapi.model.domain.UserInfo.LearningpathCombinedUser
import no.ndla.learningpathapi.model.domain.InvalidLpStatusException
import no.ndla.learningpathapi.repository.LearningPathRepositoryComponent
import no.ndla.network.clients.{FeideApiClient, MyNDLAApiClient, RedisClient}
import no.ndla.network.clients.MyNDLAApiClient
import no.ndla.network.model.{CombinedUser, CombinedUserRequired}

import scala.math.max
import scala.util.{Failure, Success, Try}

trait ReadService {
this: LearningPathRepositoryComponent & FeideApiClient & ConverterService & Clock & RedisClient & MyNDLAApiClient =>
this: LearningPathRepositoryComponent & ConverterService & Clock & MyNDLAApiClient =>
val readService: ReadService

class ReadService {
Expand Down
Loading

0 comments on commit cb84e1a

Please sign in to comment.