io.stallion.restfulEndpoints.QueryToPager.java Source code

Java tutorial

Introduction

Here is the source code for io.stallion.restfulEndpoints.QueryToPager.java

Source

/*
 * Stallion Core: A Modern Web Framework
 *
 * Copyright (C) 2015 - 2016 Stallion Software LLC.
 *
 * This program is free software: you can redistribute it and/or modify it under the terms of the
 * GNU General Public License as published by the Free Software Foundation, either version 2 of
 * the License, or (at your option) any later version. This program is distributed in the hope that
 * it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public
 * License for more details. You should have received a copy of the GNU General Public License
 * along with this program.  If not, see <http://www.gnu.org/licenses/gpl-2.0.html>.
 *
 *
 *
 */

package io.stallion.restfulEndpoints;

import java.util.*;

import static io.stallion.utils.Literals.*;

import io.stallion.dataAccess.Model;
import io.stallion.dataAccess.ModelController;
import io.stallion.dataAccess.filtering.*;
import io.stallion.requests.IRequest;
import io.stallion.services.Log;
import io.stallion.utils.json.JSON;
import org.apache.commons.lang3.StringUtils;

public class QueryToPager<T extends Model> {
    /*
       .filter()
    .exclude()
    .allSortable()
    .allFilters()
    .allowedFilters()
    .allowedSortable()
    .searchFields()
    .pageSize()
    .pager()
    .chain();
        
     */
    private FilterChain<T> chain;
    private ModelController<T> controller;
    private IRequest request;
    private List<String> _allowedFilters = list();
    private List<String> _allowedSortable = list();
    private List<String> _searchFields = list();
    private boolean _allFilters = false;
    private boolean _allSorts = false;
    private Integer _pageSize = 50;
    private boolean _requestProcessed = false;
    private String defaultSort = "";
    private boolean idAsSecondarySort = true;

    public QueryToPager(IRequest request, ModelController<T> controller) {
        this(request, controller, controller.filterChain());
    }

    public QueryToPager(IRequest request, ModelController<T> controller, FilterChain<T> chain) {
        this.request = request;
        this.controller = controller;
        this.chain = chain;
    }

    public QueryToPager<T> filter(String name, Object value, FilterOperator op) {
        this.chain = chain.filterBy(name, value, op);
        return this;
    }

    public QueryToPager<T> exclude(String name, Object value, FilterOperator op) {
        this.chain = chain.excludeBy(name, value, op);
        return this;
    }

    public QueryToPager<T> allowedFilters(String... fields) {
        this._allowedFilters = asList(fields);
        return this;
    }

    public QueryToPager<T> allowedSortable(String... fields) {
        this._allowedSortable = asList(fields);
        return this;
    }

    public QueryToPager<T> searchFields(String... fields) {
        this._searchFields = asList(fields);
        return this;
    }

    public QueryToPager<T> andAnyOf(Or... ors) {
        this.chain = chain.andAnyOf(ors);
        return this;
    }

    public QueryToPager<T> allSortable() {
        this._allSorts = true;
        return this;
    }

    public QueryToPager<T> allFilters() {
        this._allFilters = true;
        return this;
    }

    public QueryToPager<T> pageSize(Integer pageSize) {
        this._pageSize = pageSize;
        return this;
    }

    public FilterChain<T> chain() {
        if (!_requestProcessed) {
            process();
            this._requestProcessed = true;
        }
        return this.chain;
    }

    public Pager<T> pager() {
        if (!_requestProcessed) {
            process();
            this._requestProcessed = true;
        }
        Integer page = 1;
        if (!empty(request.getParameter("page"))) {
            page = Integer.parseInt(request.getParameter("page"));
        }

        return this.chain.pager(page, _pageSize);

    }

    protected void process() {
        // ?filters=&search=&page=&sort=&filter_by...
        Map<String, String> params = this.request.getQueryParams();
        String search = params.getOrDefault("search", null);
        if (!empty(search)) {
            if (!empty(_searchFields)) {
                this.chain = chain.search(search, asArray(_searchFields, String.class));
            } else {
                Log.warn("Search included, but no search fields defined");
            }
        }
        String filters = params.getOrDefault("filters", null);
        if (!empty(filters)) {
            List<LinkedHashMap> filterObjects = JSON.parseList(filters);
            for (LinkedHashMap<String, Object> o : filterObjects) {
                String field = o.get("name").toString();
                if (!_allFilters && !_allowedFilters.contains(field)) {
                    Log.warn("Filter not allowed: " + field);
                    continue;
                }

                Object value = o.get("value");
                if (value instanceof Collection) {
                    value = new ArrayList((Collection) value);
                }
                String operation = (String) o.getOrDefault("op", "=");
                this.chain = chain.filter(field, value, operation);
            }
        }
        String sort = or(params.getOrDefault("sort", null), defaultSort);
        if (!empty(sort)) {
            SortDirection dir = SortDirection.ASC;
            if (sort.startsWith("-")) {
                sort = sort.substring(1);
                dir = SortDirection.DESC;
            }
            if (!_allSorts && !_allowedSortable.contains(sort)) {
                Log.warn("Sort not allowed: " + sort);
            } else {
                this.chain = chain.sortBy(sort, dir);
            }
        }

        for (String filter : request.getQueryParamAsList("filter_by")) {
            if (empty(filter) || !filter.contains(":")) {
                continue;
            }
            String[] parts = StringUtils.split(filter, ":", 3);
            String key = parts[0];
            if (_allFilters && !_allowedFilters.contains(key)) {
                Log.warn("Filter not allowed: " + key);
                continue;
            }
            String val;
            String op = "eq";
            if (parts.length > 2) {
                op = parts[1];
                val = parts[2];
            } else {
                val = parts[1];
            }
            this.chain = chain.filter(key, val, op);

        }

    }

    public QueryToPager setDefaultSort(String defaultSort) {
        this.defaultSort = defaultSort;
        return this;
    }

    public FilterChain<T> getChain() {
        return chain;
    }

    public QueryToPager setChain(FilterChain<T> chain) {
        this.chain = chain;
        return this;
    }
}