# Filter table values based on queryParams

**URL:** <https://discuss.emberjs.com/t/filter-table-values-based-on-queryparams/18682>\
**Category:** General\
**Created:** [March 3, 2021, 12:22pm UTC](https://discuss.emberjs.com/t/filter-table-values-based-on-queryparams/18682 "2021-03-03T12:22:14Z")\
**Posts on this page:** 7\
**Page:** 1

<div class="post-metadata">

**Author:** ![Abdullah\_Ali](https://avatars.discourse-cdn.com/v4/letter/a/5daacb/32.png) [@Abdullah\_Ali](https://discuss.emberjs.com/u/Abdullah_Ali)\
**Post date:** [March 3, 2021, 12:22pm UTC](https://discuss.emberjs.com/t/filter-table-values-based-on-queryparams/18682/1 "2021-03-03T12:22:14Z")

</div>

Hello. I am implementing a filter table. After writing on the input fields and pressing the button. The value of the title is read and queryParams in the adapter is updated. Can anyone tell me how to update the table when queryParams are defined. This is the action

```auto
filterDocuments(param) {
        if (param !== '') {
          let model=this.modelFor("main.documents.table")
          var dcTitle=Ember.get(model,"dcTitle")
          this.get('documentsAdapter').filterDocuments(dcTitle, 1, ENV.APP.pageSize)

```

and my documentsAdapter is like this

```auto
export default Service.extend({
  ajax: inject('ajax'),
  session: inject('session'),
 
filterDocuments(dcTitle, page, pageSize) {
       debugger;
       let queryParams = '';
      if(!isEmpty(page)){
        queryParams+=`page=${page}`
      }
      else{
        queryParams+='page=1'
      }
      if(!isEmpty(pageSize)){
        queryParams+=`&page_size=${pageSize}`
      }
      else{
        queryParams+='&page_size=15'
      }
      if(!isEmpty(dcTitle)){
        queryParams+=`&dc_title=${dcTitle}`
      }
      return this.get('ajax').request({
      url:
      `/admins/documents?${queryParams}`,
    });
  },

```

I want to know how can I get the url generated by the adapter and then show the table that matches the title entered.

---

<div class="post-metadata">

**Author:** ![dknutsen](https://sea1.discourse-cdn.com/flex019/user_avatar/discuss.emberjs.com/dknutsen/32/16471_2.png) [@dknutsen](https://discuss.emberjs.com/u/dknutsen)\
**Post date:** [March 3, 2021, 3:32pm UTC](https://discuss.emberjs.com/t/filter-table-values-based-on-queryparams/18682/2 "2021-03-03T15:32:36Z")

</div>

Hi @Abdullah_Ali, seems like you’re doing a lot of unnecessary work here. Building the request URL and such is usually the responsibility of the data layer and Ember Data can handle this automatically. Typically what I would do in a scenario like this is the following:

1. Define your query params on your route and probably your controller as well. Something like this:

```auto
// your-route.js
export default class YourRoute extends Route {
  @service store;

  queryParams = {
    page: {
      refreshModel: true
    },
    per_page: {
      refreshModel: true
    },
    dc_title: {
      refreshModel: true
    }
  };

  model(params) {
    return this.store.query('document', params);
  }
  ...

```

This will set up the route so it queries the backend correctly based on your query params and will refresh the server request query any time your query params change.

1. Bind your query params to your route’s controller:

```auto
// your-controller.js
...
export default class YourController extends Controller {
  queryParams = [{
    page: 'page'
  }, {
    perPage: 'per_page'
  }, {
    dcTitle: 'dc_title'
  }];

  page = 1;
  pageSize = <default page size>;
  dcTitle = null;
}

```

This binds the (Ember) query params to your controller, so if you set any of the properties on your controller (let’s say you set “perPage” on the controller) it will update the corresponding query param in the page URL and then refresh your route model, which will then send the model changes to the controller and the route template rerendering the table.

That way you don’t need any of the custom adapter code or the more complex action, all you need to do is set any of those properties on the controller and everything else happens for you.

---

<div class="post-metadata">

**Author:** ![Abdullah\_Ali](https://avatars.discourse-cdn.com/v4/letter/a/5daacb/32.png) [@Abdullah\_Ali](https://discuss.emberjs.com/u/Abdullah_Ali)\
**Post date:** [March 3, 2021, 9:19pm UTC](https://discuss.emberjs.com/t/filter-table-values-based-on-queryparams/18682/3 "2021-03-03T21:19:16Z")

</div>

Thanks for the reply @dknutsen, thing is we are not using store in this project instead the adapters are used. And I already defined the `queryParams` as you suggested in my `route.js` already. As you can see in the screenshot I attached I got the url that is needed

 ![image](https://us1.discourse-cdn.com/flex019/uploads/emberjs_public/original/3X/6/8/684b166b452883b9d8abbafe831a9ed3a4019375.png) . I just want to pass this url to my route so that the url looks something like this: `example.com/documents?page=1&pageSize=15&dcTitle=towards` and then render the table based on the queryParams.

---

<div class="post-metadata">

**Author:** ![dknutsen](https://sea1.discourse-cdn.com/flex019/user_avatar/discuss.emberjs.com/dknutsen/32/16471_2.png) [@dknutsen](https://discuss.emberjs.com/u/dknutsen)\
**Post date:** [March 3, 2021, 9:52pm UTC](https://discuss.emberjs.com/t/filter-table-values-based-on-queryparams/18682/4 "2021-03-03T21:52:41Z")

</div>

Ah sorry I wrongfully assumed you were using ember data since you were using “adapter” terminology.

I would put something like this in your router:

```auto
  model({ dcTitle, page, pageSize }) {
    return this.get('documentsAdapter').filterDocuments(dcTitle, page, pageSize);
  }

```

And make sure the query params are bound on your controller. Then anytime you want the route to update you just need to set one or more of those props on the controller. This could be done on button press, on input, etc.

---

<div class="post-metadata">

**Author:** ![Abdullah\_Ali](https://avatars.discourse-cdn.com/v4/letter/a/5daacb/32.png) [@Abdullah\_Ali](https://discuss.emberjs.com/u/Abdullah_Ali)\
**Post date:** [March 4, 2021, 6:29am UTC](https://discuss.emberjs.com/t/filter-table-values-based-on-queryparams/18682/5 "2021-03-04T06:29:46Z")

</div>

@dknutsen I have an input tag on template that enables an action `filterDocuments(param)` that I defined above. My model looks like this:

```auto
model(e){
//initializations
return this.get('documents.Adapter')
    .queryDocumentsForTable(parameters)//adapter
       .then((resp)=>{
return {
//return data
}
})
}

```

And I used controllers as you suggested. Didn’t work. Ideally I would like `route.js` for actions and only use controllers to bind the binding and not use it at all.

---

<div class="post-metadata">

**Author:** ![dknutsen](https://sea1.discourse-cdn.com/flex019/user_avatar/discuss.emberjs.com/dknutsen/32/16471_2.png) [@dknutsen](https://discuss.emberjs.com/u/dknutsen)\
**Post date:** [March 4, 2021, 3:18pm UTC](https://discuss.emberjs.com/t/filter-table-values-based-on-queryparams/18682/6 "2021-03-04T15:18:51Z")

</div>

The action you defined is fetching the data itself whereas my suggestion was to just have it set one of the controller properties and let the route handle the fetch automatically.

```auto
  // controller action
  filterDocuments(param) {
    if (param === '') return;
    this.set('dcTitle', param);
  }

```

^ this would simply update the “dcTitle” prop on the controller, which would update the query param, which would cause the route model hook to refire, which would re-render the route template (and therefore your table).

> And I used controllers as you suggested. Didn’t work.

What didn’t work? What did you try?

> Ideally I would like `route.js` for actions and only use controllers to bind the binding and not use it at all.

Why is this ideal? What actions? Putting actions on a route rarely makes sense as it is one step removed from the template context and its main responsibilities can be handled via other mechanisms like query params.

---

<div class="post-metadata">

**Author:** ![Abdullah\_Ali](https://avatars.discourse-cdn.com/v4/letter/a/5daacb/32.png) [@Abdullah\_Ali](https://discuss.emberjs.com/u/Abdullah_Ali)\
**Post date:** [March 7, 2021, 7:39am UTC](https://discuss.emberjs.com/t/filter-table-values-based-on-queryparams/18682/7 "2021-03-07T07:39:59Z")

</div>

> [@dknutsen](#):
>
> Why is this ideal? What actions? Putting actions on a route rarely makes sense as it is one step removed from the template context and its main responsibilities can be handled via other mechanisms like query params.

Hi @dknutsen. I meant ideal in sense of keeping the code consistent. I am now able to filter documents based on the title I enter but there is a small bug in that way. If the search the title name and if they can not be fit in one page and if I try to move to another page the table gets updated and the titles are not filtered.

 ![image](https://us1.discourse-cdn.com/flex019/uploads/emberjs_public/original/3X/9/b/9b50b4a6913fbd70f1180953b4ba250c9b729f16.png) if the page size is 2 and the values returned are more than that it doesn’t show on the next page.

I used actions to filter the document

```auto
export default Route.extend({
  queryParams: {
    page: {
      refreshModel: true,
// set this true because data doesn't update when page is changed
    },
    pageSize: {
      refreshModel: false,
    },
    dcTitle:{
      refreshModel: false,
    },
  },
  async model(e) {
    let page = parseInt(e.page) || 1,
      pageSize = parseInt(e.pageSize) || ENV.APP.pageSize;
    let dcTitle = e.dcTitle;

    // CALL ADAPTER TO GET DOCS
    return this.get('documentsAdapter')
      .queryDocs(page, pageSize)//documents from adapter
      .then((resp) => {
        return {
          results_count: resp.meta.results_count,
          document_revisions: resp.document_revisions,
          currentPage: page,
          numberPerPage: pageSize,
          isFiltered: false,
          dcTitle: resp.dc_title,
        };
      });
  },
  actions: {
      filterDocuments() {
        //filter the documents upon button click
      
          let model=this.modelFor("main.documents.table")
          var dcTitle=Ember.get(model,'dcTitle')

          this.get('documentsAdapter').filterDocuments(undefined, undefined, dcTitle,
            undefined, undefined, undefined, 1, ENV.APP.pageSize)
            .then((resp) => {
              Ember.set(model,'document_revisions',resp.document_revisions)
              this.controller.setProperties({page: 1,});
            });
        
      },

```

Will really appreciate your help
