取消Ruby on Rails中的当前/活动查询

在我的项目中,我正在运行一个返回大量数据的大量查询。 由于此查询的大小,运行时有时超过1分钟。 忽略这可能造成的其他问题,有没有办法取消当前运行的查询?

例如,用户启动查询并重定向到标准的“加载结果…”页面。 如果他们然后决定他们不再需要结果,他们可以点击“取消”按钮,这将以某种方式终止正在运行的查询。

这是可能的,怎么做?

谢谢!

尝试使用pg_cancel_backend 。

来自文档:

取消后端的当前查询。 您可以针对与调用该函数的用户具有完全相同角色的另一个后端执行此操作。 在所有其他情况下,您必须是超级用户。

我知道的唯一方法是重新启动数据库,尽管有时您可以发送取消信号,具体取决于数据库设置。 您可以查看机架超时gem吗?

真正的问题是您的查询不应该花那么长时间,我强烈建议不要以这种方式处理问题。 一种更好的方法是检查查询并尝试优化它。 如果有任何查询合理地需要花费1分钟才能完成,那么很少。 获取数据转储到本地计算机上并在查询上运行EXPLAIN以查找瓶颈。 通过添加正确的索引,我得到了大的142s查询到<3s,所以如果你不能得到相同的效果我会感到惊讶。

我最近做了类似的事情(在我们的应用程序中添加了“取消”按钮)。 我一起攻击的plpgsql函数在下面,它基本上是pg_cancel_backend()函数的包装器。

注意事项:

1)。 您的应用程序必须创建唯一的ID(或UUID),并将其作为“p_uid”参数传递给该函数。

2)。 我硬编码了应用程序用户(不会改变)。

3)。 Postgresql 9.0+(这是为9.2创建的,在任何早期版本中未经测试)

4)。 该function可以加强安全性。

 CREATE OR REPLACE FUNCTION public.cancel_user_query(p_uid TEXT, OUT retval BOOLEAN) RETURNS boolean AS $function$ DECLARE BEGIN /* The pg_sleep() call at the start is because if a user issues a query then promptly tries to kill it, it will likely not have shown up in the pg_stat_activity view yet (there is a delay before it appears). XXX: The GUC setting "track_activities" *MUST* be enabled for this to work. */ retval := FALSE; IF ( current_setting('track_activities')::BOOLEAN IS NOT TRUE ) THEN RAISE WARNING '[PUBLIC.CANCEL_USER_QUERY] - "track_activities" *MUST* be enabled for this to work'; RETURN; END IF; /* In a system under regular high load, this might need to be bumped higher than 2 seconds */ PERFORM pg_sleep(2); WITH q AS ( SELECT pid FROM pg_stat_activity WHERE LOWER(usename) = 'YOUR_APP_USER' AND application_name = p_uid AND state <> 'idle' ) SELECT pg_cancel_backend(pid) AS retval INTO retval FROM q; if ( retval IS NOT TRUE ) then retval := FALSE; end if; RETURN; EXCEPTION WHEN others THEN RAISE WARNING '[PUBLIC.CANCEL_USER_QUERY] - ERROR: %',sqlerrm; retval := FALSE; RETURN; END; $function$ LANGUAGE plpgsql SECURITY DEFINER; 

单击“取消查询”按钮,应用程序执行该function并检查返回的状态。 例如。 SELECT retval FROM public.cancel_user_query('asifdaqiwaviafasdf') retval