<commit_before>const getKey = aggregateIds =>
  Array.isArray(aggregateIds) ? aggregateIds.sort().join(',') : aggregateIds

const buildViewModel = async (
  pool,
  aggregateIds,
  aggregateArgs,
  jwtToken,
  key
) => {
  const viewModelName = pool.viewModel.name

  await Promise.resolve()
  const snapshotKey = `${pool.viewModel.invariantHash};${key}`
  let aggregatesVersionsMap = new Map()
  let cursor = null
  let state = null

  try {
    const snapshot = JSON.parse(
      await pool.snapshotAdapter.loadSnapshot(snapshotKey)
    )
    aggregatesVersionsMap = new Map(snapshot.aggregatesVersionsMap)
    state = await pool.viewModel.deserializeState(snapshot.state)
    cursor = snapshot.cursor
  } catch (error) {}

  if (cursor == null && typeof pool.viewModel.projection.Init === 'function') {
    state = pool.viewModel.projection.Init()
  }

  let eventCount = 0

  const handler = async event => {
    const segment = pool.performanceTracer
      ? pool.performanceTracer.getSegment()
      : null
    const subSegment = segment ? segment.addNewSubsegment('applyEvent') : null

    try {
      if (!pool.workers.has(key)) {
        throw new Error(
          `View model "${viewModelName}" build has been interrupted`
        )
      }

      eventCount++

      if (subSegment != null) {
        subSegment.addAnnotation('viewModelName', viewModelName)
        subSegment.addAnnotation('eventType', event.type)
        subSegment.addAnnotation('origin', 'resolve:query:applyEvent')
      }

      state = await pool.viewModel.projection[event.type](
        state,
        event,
        aggregateArgs,
        jwtToken
      )
      cursor = pool.eventStore.getNextCursor(cursor, [event])

      aggregatesVersionsMap.set(event.aggregateId, event.aggregateVersion)

      if (pool.snapshotAdapter != null) {
        await pool.snapshotAdapter.saveSnapshot(
          snapshotKey,
          JSON.stringify({
            aggregatesVersionsMap: Array.from(aggregatesVersionsMap),
            state: await pool.viewModel.serializeState(state),
            cursor
          })
        )
      }
    } catch (error) {
      if (subSegment != null) {
        subSegment.addError(error)
      }<commit_msg>View model encryption<commit_after>import debugLevels from 'resolve-debug-levels'

const log = debugLevels('resolve:resolve-query:wrap-view-model')

const getKey = aggregateIds =>
  Array.isArray(aggregateIds) ? aggregateIds.sort().join(',') : aggregateIds

const buildViewModel = async (
  pool,
  aggregateIds,
  aggregateArgs,
  jwtToken,
  key
) => {
  const viewModelName = pool.viewModel.name

  await Promise.resolve()
  const snapshotKey = `${pool.viewModel.invariantHash};${key}`
  let aggregatesVersionsMap = new Map()
  let cursor = null
  let state = null

  try {
    const snapshot = JSON.parse(
      await pool.snapshotAdapter.loadSnapshot(snapshotKey)
    )
    aggregatesVersionsMap = new Map(snapshot.aggregatesVersionsMap)
    state = await pool.viewModel.deserializeState(snapshot.state)
    cursor = snapshot.cursor
  } catch (error) {}

  if (cursor == null && typeof pool.viewModel.projection.Init === 'function') {
    state = pool.viewModel.projection.Init()
  }

  let eventCount = 0

  const handler = async event => {
    const segment = pool.performanceTracer
      ? pool.performanceTracer.getSegment()
      : null
    const subSegment = segment ? segment.addNewSubsegment('applyEvent') : null

    try {
      if (!pool.workers.has(key)) {
        throw new Error(
          `View model "${viewModelName}" building has been interrupted`
        )
      }

      eventCount++

      if (subSegment != null) {
        subSegment.addAnnotation('viewModelName', viewModelName)
        subSegment.addAnnotation('eventType', event.type)
        subSegment.addAnnotation('origin', 'resolve:query:applyEvent')
      }

      log.debug(`retrieving event store secrets manager`)
      const secretsManager = await pool.eventStore.getSecretsManager()

      log.debug(`building view-model encryption`)
      const encryption = await pool.viewModel.encryption(event, {
        secretsManager
      })

      state = await pool.viewModel.projection[event.type](
        state,
        event,
        aggregateArgs,
        {
          jwt: jwtToken,
          ...encryption
        }
      )
      cursor = pool.eventStore.getNextCursor(cursor, [event])

      aggregatesVersionsMap.set(event.aggregateId, event.aggregateVersion)

      if (pool.snapshotAdapter != null) {
        await pool.snapshotAdapter.saveSnapshot(
          snapshotKey,
          JSON.stringify({
            aggregatesVersionsMap: Array.from(aggregatesVersionsMap),
            state: await pool.viewModel.serializeState(state),
            cursor
          })
        )
      }
    } catch (error) {
      if (subSegment != null) {
        subSegment.addError(error)
      }
{'fraction_non_alphanumeric': 0.10663119115841178, 'fraction_numerical': 0.00040933278755628325, 'mean_word_length': 2.7679259830377796, 'pattern_counts': {'":': 0, '<': 3, '<?xml version=': 0, '>': 9, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '6339550', 'n_tokens_mistral': 1401, 'n_tokens_neox': 1385, 'n_words': 282}