laravel5怎么在路由中使用数据库查询
Posted
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了laravel5怎么在路由中使用数据库查询相关的知识,希望对你有一定的参考价值。
OQL是我设计用来处理PDF.NET开发框架的ORM查询的,因此叫做ORM查询语言。自2006年第一版以来,经历了多次重构,到PDF.NET Ver 4.X 版本,已经比较稳定了,在我做的项目和框架用户朋友的项目中得到成功应用,基本符合一般的常规应用需求。OQL有下面3个显著特点:
抽象的SQL,屏蔽了具体数据库的差异,因此支持所有数据库;
对象化的“SQL”,写OQL代码能够获得IDE的智能提示,能够得到编译时检查确保不会写出错误的SQL;
没有使用.NET的特性,比如泛型、反射、表达式树等东西,因此理论上OQL可以跨语言平台,比如移植到Java,C++,VB等。
OQL的原理基于2大特性:
表达式的链式调用
属性的实例调用
OQL支持4大类数据操作
数据查询:
单实体类(单表)查询
多实体类(多表)关联查询
数据修改
更新数据
删除数据
统计、聚合运算
OQL分页 参考技术A Route::model('user','User');
Route::get('/hi', function()
header('content-type:text/html;charset=utf8');
//$rs=DB::select('select * from cf_user limit 0,100');
$rs=User::find();
dd($rs);
//return"hi";
);
数据库:
数据库配置:
'mysql' => [
'driver' => 'mysql',
'host' => 'localhost',
//'host' => env('DB_HOST', 'localhost'),
'database' => 'test',
//'database' => env('DB_DATABASE', 'forge'),
'username' => 'root',
//'username' => env('DB_USERNAME', 'forge'),
'password' => 'qaz123',
//'password' => env('DB_PASSWORD', ''),
'charset' => 'utf8',
'collation' => 'utf8_unicode_ci',
'prefix' => '',
'strict' => false,
],
使用 Laravel 在 Azure 中来自单个请求的多个重复 HTTP 请求/查询
【中文标题】使用 Laravel 在 Azure 中来自单个请求的多个重复 HTTP 请求/查询【英文标题】:Multiple duplicate HTTP requests/queries from single requests in Azure with Laravel 【发布时间】:2019-05-06 10:11:20 【问题描述】:我在 Azure 上提供了一个 Laravel 应用程序。我正在使用 AJAX 请求来轮询 javascript 图表的数据。
AJAX 请求在我的路由 (web.php) 中定义的 URL,因此:
Route::get('/rfp_chart_data', 'DataController@chart_data')->name('chart_data');
该控制器方法运行一个 postgresql 查询并返回一个 JSON 文件。这一切都很好。
但是,在遇到一些性能问题后,我决定监控 postgres 查询,发现对于此 URL 的每个请求,相同的查询运行了 3 次。
无论我是否:
通过 AJAX 请求访问 URL
在浏览器中直接访问网址
通过 cURL 访问 URL
这(AFAIK)消除了这是某种缺少 img src 问题的可能性(例如What can cause a double page request?)
非常感谢您的帮助...
编辑:
postgres pg_stat_activity 中重复查询的图像 -- 这是来自 1 个网络请求:
编辑:
完整的控制器代码:
<?php
namespace App\Http\Controllers;
use App\AllRfpEntry;
use DB;
use Illuminate\Http\Request;
use Yajra\Datatables\Facades\Datatables;
class DataController extends Controller
/**
* Displays datatables front end view
*
* @return \Illuminate\View\View
*/
//|| result_url || '\">' || result_title || '</a>'
public function chart_data(Request $request)
$binding_array = array();
$chart_data_sql = "SELECT relevant_dates.date::date,
CASE WHEN award_totals.sum IS NULL
THEN 0
ELSE award_totals.sum
END
as sum
,
CASE WHEN award_totals.transaction_count IS NULL
THEN 0
ELSE award_totals.transaction_count
END
as transaction_count FROM
(
SELECT * FROM generate_series('" . date('Y-m-01', strtotime('-15 month')) . "'::date, '" . date('Y-m-01') . "'::date, '1 month') AS date
) relevant_dates
LEFT JOIN
(
SELECT extract(year from awarded_date)::text || '-' || RIGHT('0' || extract(month from awarded_date)::text, 2) || '-01' as date, sum(award_amount)::numeric as sum, COUNT(award_amount) as transaction_count FROM all_rfp_entries
WHERE awarded_date >= '" . date('Y-m-01', strtotime('-15 month')) . "'
AND awarded_date <= '" . date("Y-m-d") . "' AND award_status = 'AWARDED'
AND award_amount::numeric < 10000000000";
if ($request->get('rfp_company_filter'))
$binding_array['rfp_company_filter'] = $request->get('rfp_company_filter');
$chart_data_sql .= " AND company = :rfp_company_filter";
;
if ($request->get('rfp_source_filter'))
$binding_array['rfp_source_filter'] = $request->get('rfp_source_filter');
$chart_data_sql .= " AND rfp_source = :rfp_source_filter";
if ($request->get('exclude_fed_rev'))
$chart_data_sql .= " AND rfp_source != 'US FED REV' ";
if ($request->get('rfp_year_filter'))
$binding_array['rfp_year_filter'] = $request->get('rfp_year_filter');
$chart_data_sql .= " AND year = :rfp_year_filter";
if ($request->get('rfp_priority_level_filter'))
$binding_array['rfp_priority_level_filter'] = $request->get('rfp_priority_level_filter');
$chart_data_sql .= " AND priority_level = :rfp_priority_level_filter";
if ($request->get('rfp_search_input_chart'))
$binding_array['rfp_search_input_chart'] = $request->get('rfp_search_input_chart');
$chart_data_sql .= " AND search_document::tsvector @@ plainto_tsquery('simple', :rfp_search_input_chart)";
$chart_data_sql .= " GROUP BY extract(year from awarded_date), extract(month from awarded_date)
) award_totals
on award_totals.date::date = relevant_dates.date::date
ORDER BY extract(year from relevant_dates.date::date), extract(month from relevant_dates.date::date)
";
return json_encode(DB::select($chart_data_sql, $binding_array));
public function data(Request $request)
$query = AllRfpEntry::select('id', 'year', 'company', 'result_title', 'award_amount', 'edit_column', 'doc_type', 'rfp_source', 'posted_date', 'awarded_date', 'award_status', 'priority_level', 'word_score', 'summary', 'contract_age', 'search_document', 'link');
if ($request->get('exclude_na'))
$query->where('all_rfp_entries.company', '!=', 'NA');
if ($request->get('clicked_date'))
$query->where('all_rfp_entries.awarded_date', '>', $request->get('clicked_date'));
$query->where('all_rfp_entries.awarded_date', '<=', $request->get('clicked_date_plus_one_month'));
if ($request->get('filter_input'))
$query->whereRaw("search_document::tsvector @@ plainto_tsquery('simple', '" . $request->get('filter_input') . "')");
$datatables_json = datatables()->of($query)
->rawColumns(['result_title', 'edit_column', 'link'])
->orderColumn('award_amount', 'award_amount $1 NULLS LAST')
->orderColumn('priority_level', 'priority_level $1 NULLS LAST');
if (!$request->get('filter_input'))
$datatables_json = $datatables_json->orderByNullsLast();
if (!$request->get('filter_input') and !$request->get('clicked_date'))
$count_table = 'all_rfp_entries';
$count = DB::select(DB::raw("SELECT n_live_tup FROM pg_stat_all_tables WHERE relname = :count_table "), array('count_table' => $count_table))[0]->n_live_tup;
$datatables_json = $datatables_json->setTotalRecords($count);
$datatables_json = $datatables_json->make(true);
return $datatables_json;
编辑:
更疯狂的皱纹......
我在这台服务器上的 Laravel 中有一个方法指向另一台服务器上的 postgres 数据库来摄取新数据。我刚刚发现,即使那个方法(指向外部服务器的方法)也在外部 postgres 服务器上生成多个查询!
除非我遗漏了什么,否则这可以避免 nginx 问题或我的提供程序 (Azure) 的问题,或任何一种特定方法的问题。即使是通过端口 5432 的直接数据库连接(我假设这就是 Laravel 访问外部数据库的方式)也会产生乘数效应,所以它一定是我的 Laravel 安装有问题......但没有更接近弄清楚是什么。
【问题讨论】:
您如何监控您的查询?您是在查看服务器日志还是通过应用程序中的一些调试器执行此操作? 我正在实时观看它们:SELECT pg_stat_activity.pid, now() - pg_stat_activity.query_start AS 持续时间, pg_stat_activity.query, pg_stat_activity.state FROM pg_stat_activity;; 我错了——我的本地 vagrant 系统也出现了这个问题。查询发生得太快,无法实时查看。所以这似乎不是 Azure 问题。 我认为这与datatables()
方法调用有关。如果您查看您发布的查询,它是最有可能用于分页的聚合计数(它需要知道有多少东西才能说出有多少页,对吧?)不知道该方法是什么/确实,我不能更具体。但我相信您的问题在于该实施。
你的路由指向DataController@chart_data
,但是控制器没有那个方法
【参考方案1】:
调试此问题的最佳方法是使用 xdebug 启动调试会话并单步执行代码,同时在单独的窗口中关注 stdout/logging 输出。
在控制器的第一行设置一个断点,当它中断时应该完成 0 个查询。如果不是,您知道路由/请求中发生了一些奇怪的事情。然后逐步执行用于构建查询的函数调用。
可能是您使用触发器执行查询的功能之一(如 Aaron Saray 所建议)或缺少方法(如 Diogo Gomes 所建议),但如果不知道代码或逐步执行,这很难说上下文一步一步。
如果您没有调试器,您可以随时在任何行使用dd($data);
来停止处理并转储给定的数据。这将需要更长的时间,因为您将为代码中的每个步骤执行一个新请求。
【讨论】:
【参考方案2】:对于它的价值,我将其追踪到多个 postgres 工作进程(您可以在 postgres .conf 文件中设置)。所以,不是错误,也不是 Laravel 的问题——只是 postgres 产生的并行工作者。
【讨论】:
以上是关于laravel5怎么在路由中使用数据库查询的主要内容,如果未能解决你的问题,请参考以下文章