Skip to content
Snippets Groups Projects
Select Git revision
  • aba12abb48a0a0192c704bdd6bdf3c083bfb70d7
  • master default protected
  • suppression_allegements_specifiques
  • budgetaire_retraites_plf
  • doc-script-gen-off-tests
  • 366-signe-a-cote-du-droit-en-vigueur-sur-l-ui-pour-indiquer-que-la-reforme-a-eu-lieu-mais-qu-elle-n
  • revalo_retraites
  • 381-pb-affichage-labels-des-parametres-sur-plus-de-3-lignes
  • ajoute-duplicate-aide-logement
  • poc_castype_ia
  • parametres-editables-budget
  • ui-parametres
  • 355-les-dispositifs-prestations-sociales-du-graphique-se-cachent-montrent-en-meme-temps-2
  • 358-les-variables-dont-le-montant-est-nul-apparaissent-en-bleu-et-non-cliquables
  • 356-ajuster-la-largeur-sur-les-graphiques-budgetaires
  • incoherence_cas_type_0
  • fix-ui-suppression-tranches-baremes
  • ajout-agregat-cehr-version-plf
  • impact_carbone
  • xlsx
  • header_revamp
  • 0.0.1191
  • 0.0.1190
  • 0.0.1189
  • 0.0.1188
  • 0.0.1187
  • 0.0.1186
  • 0.0.1185
  • 0.0.1184
  • 0.0.1183
  • 0.0.1182
  • 0.0.1181
  • 0.0.1180
  • 0.0.1179
  • 0.0.1178
  • 0.0.1177
  • 0.0.1176
  • 0.0.1175
  • 0.0.1174
  • 0.0.1173
  • 0.0.1172
41 results

StaticAggregates.svelte

Blame
  • situations.ts 8.38 KiB
    import type {
      Entity,
      EntityByKey,
      GroupEntity,
      Variable,
    } from "@openfisca/json-model"
    import { getRolePersonsIdKey } from "@openfisca/json-model"
    
    // import { entityByKey } from "$lib/entities"
    import testCasesCoreUnknown from "$lib/openfisca/test_cases.json"
    // import type { ValuesByCalculationNameByVariableName } from "$lib/variables"
    // import { variableSummaryByName } from "$lib/variables"
    
    export interface ActiveSlider extends Slider {
      stepValue: number
      vectorIndex: number
    }
    
    export interface Axis {
      count: number
      index?: number
      max: number
      min: number
      name: string
      period?: string
    }
    
    /// A population is either a group (a familly, etc) or a person.
    export interface Population extends PopulationWithoutId {
      id: string
    }
    
    export interface PopulationWithoutId {
      name?: string
      [key: string]:
        | { [instant: string]: boolean | number | string | null } // variable value by instant
        | string // id & name
        | string[] // ids of persons (when key is a role and entity is not a person)
    }
    
    export type Situation = {
      [entityKeyPlural: string]: { [populationId: string]: PopulationWithoutId }
    } & {
      /// The slider currently used
      slider?: ActiveSlider
      /// List of sliders that can be used for this situation
      sliders?: Slider[]
    }
    
    export type SituationWithAxes = Situation & {
      axes?: Axis[][]
    }
    
    export interface Slider {
      entity: string // Entity key
      id: string // Population ID
      max: number
      min: number
      name: string // Variable name
      // steps: number // Number of steps to use between min & max; currently always 101.
    }
    
    export const testCasesCore = testCasesCoreUnknown as unknown as Situation[]
    
    // export function buildTestCasesWithoutNonInputVariables(
    //   entityByKey: EntityByKey,
    //   inputInstantsByVariableNameArray: Array<{
    //     [name: string]: Set<string>
    //   }>,
    //   testCases: Situation[],
    // ): Situation[] {
    //   const entities = Object.values(entityByKey)
    //   testCases = [...testCases]
    //   for (let [situationIndex, situation] of testCases.entries()) {
    //     situation = testCases[situationIndex] = { ...situation }
    //     const inputInstantsByVariableName =
    //       inputInstantsByVariableNameArray[situationIndex]
    //     for (const entity of entities) {
    //       let entitySituation = situation[entity.key_plural]
    //       if (entitySituation === undefined) {
    //         continue
    //       }
    //       entitySituation = situation[entity.key_plural] = { ...entitySituation }
    //       const reservedKeys = getPopulationReservedKeys(entity)
    //       for (let [populationId, population] of Object.entries(
    //         entitySituation,
    //       ).sort(([populationId1], [populationId2]) =>
    //         populationId1.localeCompare(populationId2),
    //       )) {
    //         population = entitySituation[populationId] = { ...population }
    //         for (const [variableName, variableValueByInstant] of Object.entries(
    //           population,
    //         )) {
    //           if (reservedKeys.has(variableName)) {
    //             continue
    //           }
    //           const inputVariableValueByInstant: {
    //             [instant: string]: boolean | number | string | null
    //           } = {}
    //           const inputInstants =
    //             inputInstantsByVariableName[variableName] ?? new Set<string>()
    //           for (const [instant, variableValue] of Object.entries(
    //             variableValueByInstant,
    //           )) {
    //             if (!inputInstants.has(instant)) {
    //               // Remove calculated value.
    //               continue
    //             }
    //             inputVariableValueByInstant[instant] = variableValue
    //           }
    //           if (Object.keys(inputVariableValueByInstant).length > 0) {
    //             population[variableName] = inputVariableValueByInstant
    //           } else {
    //             delete population[variableName]
    //           }
    //         }
    //       }
    //     }
    //   }
    //   return testCases
    // }
    
    export function getPopulationReservedKeys(entity: Entity): Set<string> {
      return new Set(
        entity.is_person
          ? ["name"]
          : [
              "name",
              ...(entity as GroupEntity).roles.map((role) =>
                getRolePersonsIdKey(role),
              ),
            ],
      )
    }
    
    export function getSituationVariableValue(
      entityByKey: EntityByKey,
      situation: Situation,
      variable: Variable,
      populationId: string,
      year: number,
    ): boolean | number | string {
      const entity = entityByKey[variable.entity]
      const entitySituation = situation[entity.key_plural]
      return (
        entitySituation?.[populationId]?.[variable.name]?.[year] ??
        variable.default_value
      )
    }
    
    export function indexOfSituationPopulationId(
      entity: Entity,
      situation: Situation,
      populationId: string,
    ): number {
      const entitySituation = situation[entity.key_plural]
      return Object.keys(entitySituation)
        .sort(([populationId1], [populationId2]) =>
          populationId1.localeCompare(populationId2),
        )
        .indexOf(populationId)
    }
    
    export function* iterSituationVariablesName(
      entityByKey: EntityByKey,
      situation: Situation,
    ): Generator<string, void, unknown> {
      const variablesName = new Set<string>()
      for (const entity of Object.values(entityByKey)) {
        const reservedKeys = getPopulationReservedKeys(entity)
        for (const population of Object.values(
          situation[entity.key_plural] ?? {},
        ) as PopulationWithoutId[]) {
          for (const variableName of Object.keys(population)) {
            if (reservedKeys.has(variableName)) {
              continue
            }
            if (!variablesName.has(variableName)) {
              yield variableName
              variablesName.add(variableName)
            }
          }
        }
      }
    }
    
    export function setSituationVariableValue(
      entityByKey: EntityByKey,
      situation: Situation,
      variable: Variable,
      populationId: string,
      year: number,
      value: boolean | number | string,
    ): Situation {
      if (value == null) {
        value = variable.default_value
      }
      const entity = entityByKey[variable.entity]
      const entitySituation = situation[entity.key_plural]
      const existingValueByPeriod = entitySituation?.[populationId]?.[variable.name]
      if (
        existingValueByPeriod !== undefined &&
        existingValueByPeriod[year - 2] === value &&
        existingValueByPeriod[year - 1] === value &&
        existingValueByPeriod[year] === value
      ) {
        return situation
      }
      return {
        ...situation,
        [entity.key_plural]: {
          ...(entitySituation ?? {}),
          [populationId]: {
            ...(entitySituation?.[populationId] ?? {}),
            [variable.name]: {
              ...((
                entitySituation?.[populationId] as {
                  [key: string]: {
                    [date: string]: boolean | number | string | null
                  }
                }
              )?.[variable.name] ?? {}),
              [year - 2]: value,
              [year - 1]: value,
              [year]: value,
            },
          },
        },
      }
    }
    
    // export function updateTestCasesVariableValues(
    //   testCases: Situation[],
    //   variableName: string,
    //   valuesByCalculationNameByVariableNameArray: ValuesByCalculationNameByVariableName[],
    //   year: number,
    // ): Situation[] {
    //   const entityKey = variableSummaryByName[variableName]?.entity
    //   if (entityKey === undefined) {
    //     return testCases
    //   }
    //   const entity = entityByKey[entityKey]
    //   const values = variableValuesByName[variableName]
    //   if (values === undefined) {
    //     // Occurs for variables that are in test cases and are not calculated.
    //     // For example: variable "depcom_foyer".
    //     // For these variables, the situations shouldn't be updated.
    //     return testCases
    //   }
    
    //   return testCases.map((situation, situationIndex) => {
    //     const entitySituation = situation[entity.key_plural] ?? {}
    //     const situationPopulationCount = Object.keys(entitySituation).length
    //     const baseIndex =
    //       (situation.slider?.vectorIndex ?? 0) * situationPopulationCount
    //     for (const [situationPopulationIndex, [populationId, population]] of Object.entries(
    //       entitySituation,
    //     ).sort(([populationId1], [populationId2]) =>
    //       populationId1.localeCompare(populationId2),
    //     ).entries()) {
    //       entitySituation[populationId] = {
    //         ...(population ?? {}),
    //         [variableName]: {
    //           ...((population[variableName] ?? {}) as {
    //             [date: string]: boolean | number | string | null
    //           }),
    //           [year]: values[baseIndex + situationPopulationIndex],
    //         },
    //       }
    //     }
    //     return {
    //       ...situation,
    //       [entity.key_plural]: entitySituation,
    //     }
    //   })
    // }