Geo Primary Verification List: Hookup listbox items to UI

Why are we doing this work

This work will be behind feature flag geo_primary_verification_view

This work is focused on taking the UI started in Geo Primary Verification List: Hookup `geo_shar... (#538023 - closed) and hooking up the listbox to the data.

The listbox data will be provided by the view helpers Geo Primary Verification: View helpers (#537695 - closed) and should function similar to how the Geo Replicables UI handles the selected Replicable type.

Relevant links

  • UI issue: Geo Primary Verification List: Hookup `geo_shar... (#538023 - closed)
  • View helpers: Geo Primary Verification: View helpers (#537695 - closed)
  • Geo Replicables listbox processing: https://gitlab.com/gitlab-org/gitlab/-/blob/master/ee/app/assets/javascripts/geo_replicable/filters.js

Implementation plan

  1. Expose enabledModels to the ee/admin/data_management/index.js based on its implementation in Geo Primary Verification: View helpers (#537695 - closed) and provide it to the app as listboxItems
export const initDataManagement = () => {
  // most of file omitted

  const { enabledModels } = el.dataset;

  return new Vue({
    // omitted
    provide: {
      listboxItems: enabledModels
    },
  });
};
  1. Define the TOKEN_TYPE.MODEL in the constants.js and filters.js
// constants.js

export const TOKEN_TYPES = {
  MODEL: 'model',
};
// filters.js

import { TOKEN_TYPES } from "./constants";

export const getModelFilter = (value) => {
  return {
    type: TOKEN_TYPES.MODEL,
    value,
  };
};
  1. Add getFiltersFromQuery to created lifecycle in app.vue
export default {
  data() {
    return {
      activeFilters: [],
    }
  },
  created() {
    this.getFiltersFromQuery();
  },
  methods: {
    getFiltersFromQuery() {
      const url = new URL(window.location.href);
      const segments = pathSegments(url);
    
      this.activeFilters = [getModelFilter(segments.pop())];
    },
  },
};
  1. Add activeModel computed property and expose it to the template in app.vue
<script>
export default {
  computed: {
    activeModel() {
      const activeFilter = this.activeFilters.find(
        ({ type }) => type === TOKEN_TYPES.MODEL,
      );

      return activeFilter?.value;
    },
  },
};
</script>

<template>
  <geo-list-topbar
    :active-listbox-item="activeModel"
  </
</template>
  1. Add processFilters method to the filters.js to handle the filter when it is changed
export const processFilters = (filters) => {
  // URL Structure: /admin/data_management/${MODEL}?${FILTERS}
  const url = new URL(window.location.href);
  const query = {};

  filters.forEach((filter) => {
    if (filter.type === TOKEN_TYPES.MODEL) {
      const segments = pathSegments(url);
      segments[segments.length - 1] = filter.value;
      url.pathname = segments.join('/');
    }
  });

  return { query, url };
};
  1. Add event handler and methods for @listboxChange in app.vue
<script>
export default {
  methods: {
    onListboxChange(val) {
      // This may seem redundant but is needed when we add other filters to the `onSearch` event in later MRs
      this.onSearch([getModelFilter(val)]);
    },
    onSearch(filters) {
      const { query, url } = processFilters(filters);

      visitUrl(setUrlParams(query, url.href, true));
    },
  }
}
</script>

<template>
  <geo-list-top-bar
    @listboxChange="onListboxChange"
  />
</template>
Edited Oct 13, 2025 by 🤖 GitLab Bot 🤖
Assignee Loading
Time tracking Loading