Model returns nothing, but running Query returns records - eloquent

In my controller, I have the following code:
$threads = MessageThread::whereExists(function($query) {
$messid = '`' . env('DB_PREFIX') . 'message_threads`.`id`';
$query->select(\DB::raw(1))
->from('message_thread_participants')
->where('message_thread_participants.message_thread_id', '=', $messid); // AND message_thread_participants.user_id = ' . $user_id);
})
->orderBy('message_threads.created_at', 'DESC')
->take(30)
->get();
If I print out the resulting query using DB::getQueryLog() I get the following:
[ {
"query": "select * from bd45_message_threads where exists (select 1 from bd45_message_thread_participants where
bd45_message_thread_participants.message_thread_id = ?) order by
bd45_message_threads.created_at desc limit 30",
"bindings": [
"bd45_message_threads.id"
],
"time": 1.06 } ]
And I run that query manually (substituting the binding for the ?, I get the expected 30 results..... but the code itself returns no results... I assume it's some problem between using Models and Where Exists... but it's just a guess right now.... anyone have any clue why the query would return results in Navicat or PHPMyAdmin, but the controller returns a blank array?

I'm a little late to the party, but in case someone has the same problem, it must be beacause you have to use
->whereColumn('bd45_message_thread_participants.message_thread_id', 'bd45_message_threads.id')
to compare two columns values. The ->where expects to compare a column and a value, not another column.

Related

Question mark in laravel toSQL()

I get this output when trying to use toSQL() to debug my queries.
Laravel code:
$services = Service::latest()->where('status', '=', '0');
Output SQL:
"select * from `services` where `status` = ? order by `created_at` desc"
How can I get a proper query without ? mark? Thanks!
To view the data that will be substituted into the query string you can call the getBindings() function on the query like
below.
$query = User::first()->jobs();
dd($query->toSql(), $query->getBindings());
The array of bindings get substituted in the same order the ? appear in the SQL statement.
check this link

Codeigniter: How to increase active records in the for loop?

I'm using PostgreSQL and I have a table which includes week numbers of the year in its columns. I try to update by increasing these columns' values in nested loops.
I have the following query which attempts to increase the related field of a record.
foreach ( $updateVotes as $key => $value ) {
for ( $week = 1; $week < 53 ; $week++) {
$increaseValue = $value['week_'.$week];
$this->db->set("week_".$week , "week_".$week. " +".$increaseValue, "FALSE");
}
$this->db->where('id', $id)
->update('votes');
}
To achieve my aim, I need output like the one below:
UPDATE "votes"
SET week_1 = week_1 +20,
week_2 = week_2 +50,
...
WHERE id = 1
However, when I run the query, it produces the following SQL:
UPDATE "votes"
SET "week_1" = 'week_1 +20',
"week_2" = 'week_2 +50',
...
WHERE id = 1
As it also produces single quotes, it throws errors like this:
column 'week_1 +20' cannot found
How can I escape these single quotes and run the query successfully?
According to the official document here, you should pass FALSE (Bool) instead of "FALSE" (String) like this
$this->db->set("week_".$week , "week_".$week. " +".$increaseValue, FALSE);
Hope this helps!
Remove Double quotes from "FALSE" into FALSE

Cannot retrieve data from find query

In my Event model, I have the following function to retrieve all the events with status = 1 with a 12 limit and order according to event created DESC:
public function latestEvents() {
$this->Behaviors->load('Containable');
$result = $this->find('all' ,array('recursive' => -1, 'conditions'=> array('Event.status' => 1), 'limit' => 12, 'order' => array('Event.created DESC')));
debug($result); die();
return $result;
}
This function is not returning any data. When I change my limit to 6 and debug it returns six records but when I change my limit to more than 6 it returns (empty) this :
I even checked in my database by doing this query :
SELECT * FROM `events` WHERE `status` = 1 ORDER BY `created` DESC LIMIT 12
and this returns the desired data that I want. I even tried :
$result = $this->query('SELECT * FROM `events` WHERE `status` = 1 ORDER BY `created` DESC LIMIT 12');
but the same thing is happening with the limit (6 returns the data but more than 6 does not).
I found out that the data I was trying to debug had special characters and I had to include 'encoding' => 'utf8' in my database.php and worked like a charm. This post helped me.

Get result of raw SQL query in Laravel 5 Eloquent

I need help to build a Laravel query from my raw SQL Query. I tried many way and did not find my Luck. Can anybody help me? My Raw SQL code is given bellow.
SELECT exams. * , count( question_details.exam_id ) AS qus_enter
FROM exams
INNER JOIN question_details ON exams.id = question_details.exam_id GROUP BY exams.id
This is what I've tried:
$examListsID = DB::table('exams')
->join('question_details', function($join) {
$join->on('exams.id', '=', 'question_details.exam_id as qus_enter');
})
->whereraw('count(qus_enter) = exams.total_question')
->select('exams.id as examID','qus_enter','exams.total_question')
->count('qus_enter')
->groupby('exams.id')
->get();
$examLists = Addexam::where('id','=',$examListsID->examID)
And I Get this Error:
SQLSTATE[42000]: Syntax error or access violation: 1064 You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near 'as qus_enter where count(qus_enter) = exams.total_question' at line 1 (SQL: select count(qus_enter) as aggregate from exams inner join question_details on exams.id = question_details.exam_id as qus_enter where count(qus_enter) = exams.total_question)
$result = DB::table('exams')->join('question_details','exams.id','=','question_details.exam_id')->select([
exams.*,
DB::raw('count( question_details.exam_id ) AS qus_enter')
])->GroupBy('exams.id')->get()
Hope this helps
DB::listen(function ($data) {
var_dump($data->bindings);
dd($data->sql);
});

Having an SQL SELECT query, how do I get number of items?

I'm writing a web app in Perl using Dancer framework. The database is in sqlite and I use DBI for database interaction.
I'm fine with select statements, but I wonder is there a way to count selected rows.
E.g. I have
get '/' => sub {
my $content = database->prepare(sprintf("SELECT * FROM content LIMIT %d",
$CONTNUM));
$content->execute;
print(Dumper($content->fetchall_arrayref));
};
How do I count all items in the result without issuing another query?
What I want to achieve this way is showing 30 items per page and knowing how many pages there would be. Of course I can run SELECT COUNT (*) foo bar, but it looks wrong and redundant to me. I'm looking for a more or less general, DRY and not too heavy on database way to do so.
Any SQL or Perl hack or a hint what should I read about would be appreciated.
// I know using string concatenation for querys is bad
You have to do it the hard way: one query to get the count and another to get your desired slice of the row set:
my $count = $database->prepare('SELECT COUNT(*) FROM content');
$count->execute();
my $n = $count->fetchall_arrayref()->[0][0];
my $content = $database->prepare('SELECT * FROM content LIMIT ?');
$content->execute($CONTNUM);
#...
Not too familiar with perl, but I assume you can just store the result of $content->fetchall_arrayref and retrieve the count from that array befor you print it.
[edit]
Something like
my $ref = $content->fetchall_arrayref;
my $count = scalar(#$ref);
Don't use sqlite myself but the following might work:
select * from table join (select count(*) from table);
Whether the above works or not the first thing I'd look for is scrollable cursors if you are going to page through results - I doubt sqlite has those. However, in DBI you can use fetchall_arrayref with a max_rows to fetch a "page" at a time. Just look up the example in the DBI docs under fetchall_arrayref - it is something like this:
my $rowcache = [];
while( my $row = ( shift(#$rowcache) || shift(#{$rowcache=$sth->fetchall_arrayref(undef,100)||[]}) )
) {
# do something here
}
UPDATE: Added what you'd get with selectall_hashref assuming the table is called content with one integer column called "a":
$ perl -le 'use DBI; my $h = DBI->connect("dbi:SQLite:dbname=fred.db"); my $r = $h->selectall_hashref(q/select * from content join (select count(*) as count from content)/, "a");use Data::Dumper;print Dumper($r);'
$VAR1 = {
'1' => {
'count' => '3',
'a' => '1'
},
'3' => {
'count' => '3',
'a' => '3'
},
'2' => {
'count' => '3',
'a' => '2'
}
};
If you want to know how many results there will be, as well as getting the results themselves, all in one query, then get the count as a new value:
SELECT COUNT(*) AS num_rows, * from Table WHERE ...
Now the row count will be the first column of every row of your resultset, so simply pop that off before presenting the data.