Laravel-admin: 数据表存储的时间用的int类型时,按时间范围搜索查询过滤要如何使用?

Created on 6 May 2018  ·  10Comments  ·  Source: z-song/laravel-admin

  • Laravel Version: 5.5.#
  • PHP Version:7.0
  • Laravel-admin: 1.5.#

Description:

数据表使用的int类型存储的unix时间戳,要怎样进行查询?
$filter->between('add_time', 'Time')->datetime();
这样写模型获取到的是2018-05-06 00:00:00 这样的形式,无法查询得到结果
如果在接收数据时把接收结果换算成int类型,又会导致过滤控件中回显的时间变成int类型。
              $filter->where(function ($query) {
                    $query->where('add_time', '>=', strtotime($this->input.' 00:00:00'));
                }, 'Start')->date();

                $filter->where(function ($query) {
                    $query->where('add_time', '<=', strtotime($this->input.' 23:59:59'));
                }, 'End')->date();

上述代码可以实现,但是会生成两行,我想生成$filter->between('add_time', 'Time')->datetime();这种形式的查询过滤控件,有办法吗?

还有使用上述代码只能用date()方法,无法精确到时分秒,如果要精确到时分秒,要如何处理?

查询了很多资料都弄不明白,这个需要要怎么实现?

Steps To Reproduce:

Most helpful comment

非常感谢~按照思路得到了想要的结果

纠正一下继承的类是:Encore\Admin\Grid\Filter\Between;

贴上代码方便后面的人使用:

class TimestampBetween extends Between
{
    // 重载condition方法,
    public function condition($inputs)
    {
        // $inputs即为传进来的参数,格式化成timestamp再去构建条件

        if (!array_has($inputs, $this->column)) {
            return;
        }

        $this->value = array_get($inputs, $this->column);

        $value = array_filter($this->value, function ($val) {
            return $val !== '';
        });

        if (empty($value)) {
            return;
        }

        if (!isset($value['start'])) {


            $value['end'] = strtotime($value['end']);//转成时间戳

            return $this->buildCondition($this->column, '<=', $value['end']);
        }

        if (!isset($value['end'])) {

            $value['start'] = strtotime($value['start']);//转成时间戳

            return $this->buildCondition($this->column, '>=', $value['start']);
        }

        $this->query = 'whereBetween';

        $value['end'] = strtotime($value['end']);//转成时间戳
        $value['start'] = strtotime($value['start']);//转成时间戳


        //return $this->buildCondition($this->column, $this->value);
        //这里需要注意$this->value的值会作用于页面reset按钮,不能直接修改这个值,否则会导致按reset回显时间戳
        return $this->buildCondition($this->column, $value);


    }
}


All 10 comments

补充说明一下:

如果使用如下代码处理这个时间范围,会导致回显时按reset后回显成了int类型。无法达到想要的结果。

if (request()->has('add_time')) {
            $params = request()->all();
            request()->merge(['add_time' => ['start'=>strtotime($params['add_time']['start']),'end'=>strtotime($params['add_time']['end'])]]);
        }

image

可以自定义过滤器的,先定义一个类继承Encore\Admin\Grid\Filter\Between

class TimestampBetween extends \Encore\Admin\Grid\Filter\Between
{
    // 重载condition方法,
    public function condition($inputs)
    {
        // $inputs即为传进来的参数,格式化成timestamp再去构建条件
    }
}

然后在grid中使用这个自定义的过滤器:

$filter->use(new TimestampBetween())->datetime();

非常感谢~按照思路得到了想要的结果

纠正一下继承的类是:Encore\Admin\Grid\Filter\Between;

贴上代码方便后面的人使用:

class TimestampBetween extends Between
{
    // 重载condition方法,
    public function condition($inputs)
    {
        // $inputs即为传进来的参数,格式化成timestamp再去构建条件

        if (!array_has($inputs, $this->column)) {
            return;
        }

        $this->value = array_get($inputs, $this->column);

        $value = array_filter($this->value, function ($val) {
            return $val !== '';
        });

        if (empty($value)) {
            return;
        }

        if (!isset($value['start'])) {


            $value['end'] = strtotime($value['end']);//转成时间戳

            return $this->buildCondition($this->column, '<=', $value['end']);
        }

        if (!isset($value['end'])) {

            $value['start'] = strtotime($value['start']);//转成时间戳

            return $this->buildCondition($this->column, '>=', $value['start']);
        }

        $this->query = 'whereBetween';

        $value['end'] = strtotime($value['end']);//转成时间戳
        $value['start'] = strtotime($value['start']);//转成时间戳


        //return $this->buildCondition($this->column, $this->value);
        //这里需要注意$this->value的值会作用于页面reset按钮,不能直接修改这个值,否则会导致按reset回显时间戳
        return $this->buildCondition($this->column, $value);


    }
}


如何调用呢?为什么报Call to a member function datetime() on null错误

@amorphis666
$filter->use(new TimestampBetween('created_at'))->date();

@amorphis666 请教一下。由于结束时间我们是按照当天的23:59:59秒来算的。那么都直接在这个自定义的类里进行处理操作的吗?

@lePig 还是不行,可能是我的环境或版本问题。你的问题在这个自定义的类里操作即可。

非常感谢~按照思路得到了想要的结果

如果想在这个处理过的过滤器上面添加orWhere(),应该怎么做呢?

感谢大家的分享,我把他封装成扩展了:

https://github.com/wuwx/laravel-admin-timestamp-between

感谢大家的分享,我把他封装成扩展了:

https://github.com/wuwx/laravel-admin-timestamp-between

感谢,社区就需要您这样的

Was this page helpful?
0 / 5 - 0 ratings

Related issues

donglianyou picture donglianyou  ·  3Comments

zhenyangze picture zhenyangze  ·  3Comments

clock1129 picture clock1129  ·  3Comments

piian picture piian  ·  3Comments

fokoz picture fokoz  ·  3Comments