Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Subject index #608

Merged
merged 20 commits into from
Mar 5, 2025
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -107,12 +107,6 @@ class ArticleApiProperties extends BaseProps with DatabaseProps {
).getOrElse(Environment, "https://h5p.ndla.no")
)

def ndlaFrontendUrl: String = Environment match {
case "local" => "http://localhost:30017"
case "prod" => "https://ndla.no"
case _ => s"https://$Environment.ndla.no"
}

private def BrightcoveAccountId: String = prop("NDLA_BRIGHTCOVE_ACCOUNT_ID")
private def BrightcovePlayerId: String = prop("NDLA_BRIGHTCOVE_PLAYER_ID")

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -35,7 +35,7 @@ import no.ndla.database.{DBMigrator, DBUtility, DataSource}
import no.ndla.network.NdlaClient
import no.ndla.network.tapir.TapirApplication
import no.ndla.network.clients.{FeideApiClient, RedisClient}
import no.ndla.search.{BaseIndexService, Elastic4sClient}
import no.ndla.search.{BaseIndexService, Elastic4sClient, SearchLanguage}

class ComponentRegistry(properties: ArticleApiProperties)
extends BaseComponentRegistry[ArticleApiProperties]
Expand All @@ -52,6 +52,7 @@ class ComponentRegistry(properties: ArticleApiProperties)
with ArticleSearchService
with IndexService
with BaseIndexService
with SearchLanguage
with ArticleIndexService
with SearchService
with ConverterService
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -47,14 +47,14 @@ trait ArticleIndexService {
),
keywordField("grepCodes")
)
val dynamics = generateLanguageSupportedDynamicTemplates("title", keepRaw = true) ++
generateLanguageSupportedDynamicTemplates("content") ++
generateLanguageSupportedDynamicTemplates("visualElement") ++
generateLanguageSupportedDynamicTemplates("introduction") ++
generateLanguageSupportedDynamicTemplates("metaDescription") ++
generateLanguageSupportedDynamicTemplates("tags")

properties(fields).dynamicTemplates(dynamics)
val dynamics = generateLanguageSupportedFieldList("title", keepRaw = true) ++
generateLanguageSupportedFieldList("content") ++
generateLanguageSupportedFieldList("visualElement") ++
generateLanguageSupportedFieldList("introduction") ++
generateLanguageSupportedFieldList("metaDescription") ++
generateLanguageSupportedFieldList("tags")

properties(fields ++ dynamics)
}
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -12,20 +12,17 @@ import cats.implicits.*
import com.sksamuel.elastic4s.ElasticDsl.*
import com.sksamuel.elastic4s.fields.ElasticField
import com.sksamuel.elastic4s.requests.indexes.IndexRequest
import com.sksamuel.elastic4s.requests.mappings.dynamictemplate.DynamicTemplateRequest
import com.typesafe.scalalogging.StrictLogging
import no.ndla.articleapi.Props
import no.ndla.articleapi.repository.ArticleRepository
import no.ndla.common.model.domain.article.Article
import no.ndla.search.SearchLanguage.languageAnalyzers
import no.ndla.search.model.domain.{BulkIndexResult, ReindexResult}
import no.ndla.search.{BaseIndexService, Elastic4sClient, SearchLanguage}

import scala.collection.mutable.ListBuffer
import scala.util.{Failure, Success, Try}

trait IndexService {
this: Elastic4sClient & BaseIndexService & Props & ArticleRepository =>
this: Elastic4sClient & BaseIndexService & Props & ArticleRepository & SearchLanguage =>

trait IndexService extends BaseIndexService with StrictLogging {
override val MaxResultWindowOption: Int = props.ElasticSearchIndexMaxResultWindow
Expand Down Expand Up @@ -99,55 +96,19 @@ trait IndexService {
*/
protected def generateLanguageSupportedFieldList(fieldName: String, keepRaw: Boolean = false): Seq[ElasticField] = {
if (keepRaw) {
languageAnalyzers.map(langAnalyzer =>
SearchLanguage.languageAnalyzers.map(langAnalyzer =>
textField(s"$fieldName.${langAnalyzer.languageTag.toString}")
.fielddata(false)
.analyzer(langAnalyzer.analyzer)
.fields(keywordField("raw"))
)
} else {
languageAnalyzers.map(langAnalyzer =>
SearchLanguage.languageAnalyzers.map(langAnalyzer =>
textField(s"$fieldName.${langAnalyzer.languageTag.toString}")
.fielddata(false)
.analyzer(langAnalyzer.analyzer)
)
}
}

/** Returns Sequence of DynamicTemplateRequest for a given field.
*
* @param fieldName
* Name of field in mapping.
* @param keepRaw
* Whether to add a keywordField named raw. Usually used for sorting, aggregations or scripts.
* @return
* Sequence of DynamicTemplateRequest for a field.
*/
protected def generateLanguageSupportedDynamicTemplates(
fieldName: String,
keepRaw: Boolean = false
): Seq[DynamicTemplateRequest] = {
val fields = new ListBuffer[ElasticField]()
if (keepRaw) {
fields += keywordField("raw")
}
val languageTemplates = languageAnalyzers.map(languageAnalyzer => {
val name = s"$fieldName.${languageAnalyzer.languageTag.toString()}"
DynamicTemplateRequest(
name = name,
mapping = textField(name).analyzer(languageAnalyzer.analyzer).fields(fields.toList),
matchMappingType = Some("string"),
pathMatch = Some(name)
)
})
val catchAllTemplate = DynamicTemplateRequest(
name = fieldName,
mapping = textField(fieldName).analyzer(SearchLanguage.standardAnalyzer).fields(fields.toList),
matchMappingType = Some("string"),
pathMatch = Some(s"$fieldName.*")
)
languageTemplates ++ Seq(catchAllTemplate)
}
}

}
Original file line number Diff line number Diff line change
Expand Up @@ -13,20 +13,20 @@ import no.ndla.articleapi.model.api.{ArticleSummaryV2DTO, SearchResultV2DTO}
import no.ndla.articleapi.model.search.*
import no.ndla.articleapi.service.ConverterService
import no.ndla.common.model.domain.article.Article
import no.ndla.search.SearchLanguage.languageAnalyzers
import no.ndla.search.SearchLanguage
import no.ndla.search.model.{LanguageValue, SearchableLanguageList, SearchableLanguageValues}
import org.jsoup.Jsoup

trait SearchConverterService {
this: ConverterService =>
this: ConverterService & SearchLanguage =>
val searchConverterService: SearchConverterService

class SearchConverterService extends StrictLogging {

def asSearchableArticle(ai: Article): SearchableArticle = {
val defaultTitle = ai.title
.sortBy(title => {
val languagePriority = languageAnalyzers.map(la => la.languageTag.toString).reverse
val languagePriority = SearchLanguage.languageAnalyzers.map(la => la.languageTag.toString).reverse
languagePriority.indexOf(title.language)
})
.lastOption
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -24,7 +24,7 @@ import no.ndla.database.{DBMigrator, DBUtility, DataSource}
import no.ndla.network.NdlaClient
import no.ndla.network.clients.{FeideApiClient, RedisClient}
import no.ndla.network.tapir.TapirApplication
import no.ndla.search.{BaseIndexService, Elastic4sClient}
import no.ndla.search.{BaseIndexService, Elastic4sClient, SearchLanguage}
import org.scalatestplus.mockito.MockitoSugar

trait TestEnvironment
Expand Down Expand Up @@ -57,6 +57,7 @@ trait TestEnvironment
with Props
with TestData
with DBMigrator
with SearchLanguage
with FrontpageApiClient
with ImageApiClient {
val props: ArticleApiProperties = new ArticleApiProperties {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,7 @@ import no.ndla.common.configuration.BaseComponentRegistry
import no.ndla.database.{DBMigrator, DataSource}
import no.ndla.network.NdlaClient
import no.ndla.network.tapir.TapirApplication
import no.ndla.search.{BaseIndexService, Elastic4sClient}
import no.ndla.search.{BaseIndexService, Elastic4sClient, SearchLanguage}

class ComponentRegistry(properties: AudioApiProperties)
extends BaseComponentRegistry[AudioApiProperties]
Expand All @@ -47,6 +47,7 @@ class ComponentRegistry(properties: AudioApiProperties)
with Elastic4sClient
with IndexService
with BaseIndexService
with SearchLanguage
with AudioIndexService
with SeriesIndexService
with TagIndexService
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,6 @@ import com.sksamuel.elastic4s.ElasticDsl.*
import com.sksamuel.elastic4s.fields.{ElasticField, ObjectField}
import com.sksamuel.elastic4s.requests.indexes.IndexRequest
import com.sksamuel.elastic4s.requests.mappings.MappingDefinition
import com.sksamuel.elastic4s.requests.mappings.dynamictemplate.DynamicTemplateRequest
import com.typesafe.scalalogging.StrictLogging
import no.ndla.audioapi.Props
import no.ndla.audioapi.model.domain.AudioMetaInformation
Expand Down Expand Up @@ -74,14 +73,14 @@ trait AudioIndexService {
)
)

val dynamics: Seq[DynamicTemplateRequest] =
generateLanguageSupportedDynamicTemplates("titles", keepRaw = true) ++
generateLanguageSupportedDynamicTemplates("tags") ++
generateLanguageSupportedDynamicTemplates("manuscript") ++
generateLanguageSupportedDynamicTemplates("filePaths") ++
generateLanguageSupportedDynamicTemplates("podcastMetaIntroduction")
val dynamics =
generateLanguageSupportedFieldList("titles", keepRaw = true) ++
generateLanguageSupportedFieldList("tags") ++
generateLanguageSupportedFieldList("manuscript") ++
generateLanguageSupportedFieldList("filePaths") ++
generateLanguageSupportedFieldList("podcastMetaIntroduction")

properties(fields).dynamicTemplates(dynamics)
properties(fields ++ dynamics)
}
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -13,19 +13,16 @@ import com.sksamuel.elastic4s.ElasticDsl.*
import com.sksamuel.elastic4s.fields.ElasticField
import com.sksamuel.elastic4s.requests.indexes.IndexRequest
import com.sksamuel.elastic4s.requests.mappings.MappingDefinition
import com.sksamuel.elastic4s.requests.mappings.dynamictemplate.DynamicTemplateRequest
import com.typesafe.scalalogging.StrictLogging
import no.ndla.audioapi.Props
import no.ndla.audioapi.repository.{AudioRepository, Repository}
import no.ndla.search.SearchLanguage.languageAnalyzers
import no.ndla.search.model.domain.{BulkIndexResult, ReindexResult}
import no.ndla.search.{BaseIndexService, Elastic4sClient, SearchLanguage}

import scala.collection.mutable.ListBuffer
import scala.util.{Failure, Success, Try}

trait IndexService {
this: Elastic4sClient & BaseIndexService & SearchConverterService & AudioRepository & Props =>
this: Elastic4sClient & BaseIndexService & SearchConverterService & AudioRepository & Props & SearchLanguage =>

trait IndexService[D, T] extends BaseIndexService with StrictLogging {
override val MaxResultWindowOption: Int = props.ElasticSearchIndexMaxResultWindow
Expand Down Expand Up @@ -107,53 +104,17 @@ trait IndexService {
*/
protected def generateLanguageSupportedFieldList(fieldName: String, keepRaw: Boolean = false): Seq[ElasticField] = {
if (keepRaw) {
languageAnalyzers.map(langAnalyzer =>
SearchLanguage.languageAnalyzers.map(langAnalyzer =>
textField(s"$fieldName.${langAnalyzer.languageTag.toString()}")
.analyzer(langAnalyzer.analyzer)
.fields(keywordField("raw"))
)
} else {
languageAnalyzers.map(langAnalyzer =>
SearchLanguage.languageAnalyzers.map(langAnalyzer =>
textField(s"$fieldName.${langAnalyzer.languageTag.toString()}").analyzer(langAnalyzer.analyzer)
)
}
}

/** Returns Sequence of DynamicTemplateRequest for a given field.
*
* @param fieldName
* Name of field in mapping.
* @param keepRaw
* Whether to add a keywordField named raw. Usually used for sorting, aggregations or scripts.
* @return
* Sequence of DynamicTemplateRequest for a field.
*/
protected def generateLanguageSupportedDynamicTemplates(
fieldName: String,
keepRaw: Boolean = false
): Seq[DynamicTemplateRequest] = {
val fields = new ListBuffer[ElasticField]()
if (keepRaw) {
fields += keywordField("raw")
}
val languageTemplates = languageAnalyzers.map(languageAnalyzer => {
val name = s"$fieldName.${languageAnalyzer.languageTag.toString()}"
DynamicTemplateRequest(
name = name,
mapping = textField(name).analyzer(languageAnalyzer.analyzer).fields(fields.toList),
matchMappingType = Some("string"),
pathMatch = Some(name)
)
})
val catchAlltemplate = DynamicTemplateRequest(
name = fieldName,
mapping = textField(fieldName).analyzer(SearchLanguage.standardAnalyzer).fields(fields.toList),
matchMappingType = Some("string"),
pathMatch = Some(s"$fieldName.*")
)
languageTemplates ++ Seq(catchAlltemplate)
}

}

}
Original file line number Diff line number Diff line change
Expand Up @@ -25,7 +25,7 @@ import no.ndla.search.model.{LanguageValue, SearchableLanguageList, SearchableLa
import scala.util.Try

trait SearchConverterService {
this: ConverterService with Props =>
this: ConverterService & Props & SearchLanguage =>
val searchConverterService: SearchConverterService

class SearchConverterService extends StrictLogging {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -26,7 +26,7 @@ import no.ndla.search.{Elastic4sClient, IndexNotFoundException, NdlaSearchExcept
import scala.util.{Failure, Success, Try}

trait SearchService {
this: Elastic4sClient with SearchConverterService with Props =>
this: Elastic4sClient & SearchConverterService & Props & SearchLanguage =>

trait SearchService[T] extends StrictLogging {
import props._
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,6 @@ import com.sksamuel.elastic4s.fields.ElasticField
import com.sksamuel.elastic4s.ElasticDsl.*
import com.sksamuel.elastic4s.requests.indexes.IndexRequest
import com.sksamuel.elastic4s.requests.mappings.MappingDefinition
import com.sksamuel.elastic4s.requests.mappings.dynamictemplate.DynamicTemplateRequest
import com.typesafe.scalalogging.StrictLogging
import no.ndla.audioapi.Props
import no.ndla.audioapi.model.domain.Series
Expand All @@ -24,7 +23,7 @@ import no.ndla.search.Elastic4sClient
import scala.util.{Failure, Success, Try}

trait SeriesIndexService {
this: Elastic4sClient with SearchConverterService with IndexService with SeriesRepository with Props =>
this: Elastic4sClient & SearchConverterService & IndexService & SeriesRepository & Props =>

val seriesIndexService: SeriesIndexService

Expand All @@ -50,11 +49,11 @@ trait SeriesIndexService {
dateField("lastUpdated")
)

val seriesDynamics: Seq[DynamicTemplateRequest] =
generateLanguageSupportedDynamicTemplates("titles", keepRaw = true) ++
generateLanguageSupportedDynamicTemplates("descriptions", keepRaw = true)
val seriesDynamics =
generateLanguageSupportedFieldList("titles", keepRaw = true) ++
generateLanguageSupportedFieldList("descriptions", keepRaw = true)

def getMapping: MappingDefinition = properties(seriesIndexFields).dynamicTemplates(seriesDynamics)
def getMapping: MappingDefinition = properties(seriesIndexFields ++ seriesDynamics)
}

}
Original file line number Diff line number Diff line change
Expand Up @@ -20,7 +20,7 @@ import no.ndla.common.brightcove.NdlaBrightcoveClient
import no.ndla.database.DataSource
import no.ndla.network.NdlaClient
import no.ndla.network.tapir.TapirApplication
import no.ndla.search.{BaseIndexService, Elastic4sClient}
import no.ndla.search.{BaseIndexService, Elastic4sClient, SearchLanguage}
import org.scalatestplus.mockito.MockitoSugar

trait TestEnvironment
Expand All @@ -41,6 +41,7 @@ trait TestEnvironment
with Elastic4sClient
with IndexService
with BaseIndexService
with SearchLanguage
with AudioIndexService
with SeriesIndexService
with SearchConverterService
Expand Down
Loading