Eloquent Subquery - laravel-4

I have a many to many relationship between a student table and a apparatus table (A student performs on many apparatuses and an apparatus has many students). I have a student_results table that has a composite primary key (student_id and apparatus_id) and a 3rd field called results).
I have written a query to find all the apparatuses that a student DOES NOT have a result. The example I give is for student with id = 121.
The sub-query is.
SELECT apparatus_id, strapparatus_name FROM apparatuss
WHERE apparatus_id <> ALL(SELECT apparatus_id FROM student_results
WHERE student_id =' . 121 . ')';
I would like to write this using Eloquent (Laravel 4.1).
Any help greatly appreciated.

Assuming that you already have your Eloquent models Apparatus and StudentResult set, this is a way:
Apparatus::whereNotIn(
'apparatus_id',
StudentResult::where('student_id', 121)->lists('apparatus_id')
)->get('apparatus_id', 'strapparatus_name');
Or, if you don't have a model for your student_results table, you can just:
Apparatus::whereNotIn(
'apparatus_id',
DB::table('student_results')->where('student_id', 121)->lists('apparatus_id');
)->get(array('apparatus_id', 'strapparatus_name'));

Related

Laravel where clause of current and related table

how to compare current table column to related table column
example: A.quantity < B.criticalQuantity
similarly like this AModel::where('quantity', "<", "b.criticalQuantity")->get()
the relations is
B HasMany A
A BelongsTo B
you can use whereColumn
it is specialist in comparing columns not a column with value.
anyway you can't directly compare two columns from two table, you have to join them first by anyway of join types
something like:
$values = ModelA::join('model_b_table_name', 'model_b_table_name.id', 'model_a_table_name.model_b_id')
->whereColumn('model_b_table_name.column.quantity', 'model_b_table_name.quantity')
->get();
you must be specific in joining the table, you should join by the columns that consist the relation between the two tables.
->whereRaw('table_1.name = table_2.name')

Why Laravel does not make lots of queries when using exists on relations?

I have such entities as:
Company
Person
Company hasMany Persons. So in the persons table there is company_id column.
I return company list, which I pass to CompanyResource. There I return has_persons => $this->persons()->exists() value.
Then I checked the result of DB::getQueryLog() and I found out that there is only one SQL query, which does not have count or anything like that.
In order to count how many persons a company has, Laravel should make one query per company, shouldn't it? Like select count (*) from persons where company_id = 5 for example
try this
$this->persons->count()

Aggregate function in laravel 5.4 with joining

I have two tables :
users table
{id, name}
payments table
{id, user_id, payment}
Here I want to join two tables and want to use SUM(payment) function group by id.
please give me a solution.
You can do join like this way:
$payments = DB::table('users')->join('payments','users.id','=','payments.user_id')->groupBy('users.id')->sum('payment');
//use DB to in you controller
You can use a queryBuilder for make de custom query.

Laravel Eloquent select function cause empty relation

Following is my query
$user = User::select(['uuid','name','about'])->with(['education','work'])->first();
this returns empty data for relationship education and work,
but if I remove select function from query I am getting data in relationship and it also returns all columns of user table which I don't want.
how can solve this problem
The problem is that relationships (with(...)) execute an additional query to get the related results. Let's say you have one to many relationship where users have many works. User::with('work')->find(1) will then execute these 2 queries:
select user where id = 1 and select works where user_id = 1.
So basically in order to be able to execute the second query (fetch relationship data) you need to include id (or whichever column you're referencing) in you select statement.
Fix:
$user = User::select(['uuid','name','about', 'id'])->with(['education','work'])->first();
Same principle in different forms applies to all relationships. For example in the inverse of hasMany which is belongsTo you would need to select the foreign key (for example user_id).

Count the number of rows in many to many relationships in Hibernate

I have three of many tables in Oracle (10g) database as listed below. I'm using Hibernate Tools 3.2.1.GA with Spring version 3.0.2.
Product - parent table
Colour - parent table
ProductColour - join table - references colourId and prodId of Colour and Product tables respectively
Where the ProductColour is a join table between Product and Colour. As the table names imply, there is a many-to-many relationship between Product and ProductColour. I think, the relationship in the database can easily be imagined and is clear with only this much information. Therefore, I'm not going to explore this relationship at length.
One entity (row) in Product is associated with any number entities in Colour and one entity (row) in Colour can also be associated with any number of entities in Product.
Let's say as for an example, I need to count the number of rows available in the Product table (regarding Hibernate), it can be done something like the following.
Object rowCount = session.createCriteria(Product.class)
.setProjection(Projections.rowCount()).uniqueResult();
What if I need to count the number of rows available in the ProductColour table? Since, it is a many-to-many relationship, it is mapped in the Product and the Colour entity classes (POJOs) with there respective java.util.Set and no direct POJO class for the ProductColour table is available. So the preceding row-counting statement doesn't seem to work in this scenario.
Is there a precise way to count the number of rows of such a join entity in Hibernate?
I think you should be able to do a JPQL or HQL along the lines.
SELECT count(p.colors) FROM Product AS p WHERE p.name = :name ... other search criteria etc
or
SELECT count(c.products) FROM Color AS c WHERE c.name = :name .... other search criteria
From Comment below, this should work:
Long colours=(Long) session.createQuery("select count(*) as cnt from Colour colour where colour.colourId in(select colours.colourId from Product product inner join product.colours colours where product.prodId=:prodId)").setParameter("prodId", prodId).uniqueResult();

Resources