Convert String to Eloquent functions - php

I am building an API with laravel, so I am trying to pass Laravel's Eloquent functions as string and execute them in the controller, actually I am sending a JSON object but I am converting it to a string in backend, here is what I tried to do
API URL with parameters:
http://www.example.com/api/articles?parameters={"orderByDesc":"'created_at'", "limit":"2"}
Controller side:
$json = json_decode(request('parameters'), TRUE);
$query = '';
foreach ($json as $function => $value){
$query .= $function.'('.$value.')->';
}
$query = $query.'get();';
return $query;
Output:
orderByDesc('created_at')->limit(2)->get();
Now how can I execute this string as code on the model, example:
$articles = Article::orderByDesc('created_at')->limit(2)->get();
I couldn't concatenate like this: Article::.$query
And I can't use PHP's eval()
The idea is to use Laravel's Eloquent functions inside a JSON object and pass them in one URL parameter.
Thanks

Maybe you should try this.
$json = json_decode(request('parameters'), true);
$query = Article::query();
foreach($json as $function => $value){
$query->{$function}($value);
}
$query = $query->get();
return $query;
You can run function on object with ->{$func_name} syntax
Edit: You can pass multiple arguments too. But you can check if whether value is array or not:
foreach($json as $function => $value){
if(is_array($value)) {
$query->{$function}(...$value);
} else {
$query->{$function}($value);
}
}
In this case you can have: {"orderByDesc":"'created_at'", "limit":"2", "where": ["column_name", "LIKE", "%SOME_STRING"]} and it will generate query equivalent to: ->where('column_name', 'LIKE', '%SOME_STRING')

Related

Laravel Collection Loop to another Collection

How to loop the eloquent collection from one to another? I'm just getting first line of array. I have more than 4 array in the collection.
$queries = Students::where('year',"=", 1)->get();
$students = new Students();
foreach ($queries as $query) {
$students->name = $query->name;
$students->faculty = $query->faculty ."Add something";
$students->year = $query->year;
}
dd($students);
I want to change the collection a bit before I print to json. For example, I want add something behind the faculty
Use the transform() method to modify collection:
$students = Students::where('year', 1)->get();
$students->transform(function($i) {
$i->faculty = $i->faculty . 'add something';
return $i;
});
You also can use resource classes to transform the data before returning JSON response.
You could use map() to modify collection-
$queries = $queries->map(function($query){
$query->faculty = $query->faculty."kfjhgli";
return $query;
});
return $queries;

How to use array values outside foreach loop?

How can I use an array values outside a foreach loop in Laravel 5.4?
Here is the code :
public function index(Request $request)
{
$name = $request->input('keyword');
$category = $request->input('category');
$catkeywords = array(DB::table('keywords')->pluck($category));
foreach ($catkeywords as $catkeyword) {
$string = implode(',',$catkeyword);
}
echo $string;
}
I don't know why it doesn't work !
I just want the returned keywords from database to combine them with some text and to use for some API queries.
In other words, I want the list of keywords outside of the loop.
For using in an API query like this :
http://api-url/query?id=domain1.com,domain2.com,domain3.com
$catkeywords returns a json formatted list of keywords.
Now I want to combine these keywords with a user-inputted value and add a ".com" suffix,
then separate them using commas and use them on query url as a variable.
P.S : I'm using guzzlehttp for sending requests to the API. So it should be placed on :
'DomainList' => $domainlist
How can I do that ?
If you're using laravel, you should consider taking advantages of their collections:
https://laravel.com/docs/5.4/collections#method-implode
public function index(Request $request)
{
$name = $request->input('keyword');
$category = $request->input('category');
$catkeywords = DB::table('keywords')->implode($category, ',');
echo $catkeywords;
}
Laravel collections have a command for imploding the array, so there's no need to use pluck and loop through the array unless you plan on doing other operations on the data too.
EDIT: Based on updated question, it sounds like you're looking for something like this:
public function index(Request $request)
{
$name = $request->input('keyword');
$category = $request->input('category');
$catkeywords = DB::table('keywords')->pluck($category); //You don't need to wrap this in an array()
$keywords = []; //Create a holding array
foreach ($catkeywords as $catkeyword) {
$keywords[] = $catkeyword . '.com'; //Push the value to the array
}
echo implode(',', $keywords); //Then implode the edited values at the end
}
when you use pluck() method then it return array of given name
so you dont have need to use foreach loop
just use
$catkeywords = array(DB::table('keywords')->pluck($category));
echo implode(',',$catkeyword);
You try do that
public function index(Request $request)
{
$name = $request->input('keyword');
$string = '';
$category = $request->input('category');
$catkeywords = array(DB::table('keywords')->pluck($category));
foreach ($catkeywords as $catkeyword) {
$string .= implode(',',$catkeyword);
}
echo $string;
}

Codeigniter retrieve data immediately on controller

How can I retrieve a data from my database in the controller, and assign it to a variable, that I will send to the view?
$data['schedule'] = $this->SectionsModel->getschedule($section);
I want the
$schedule['teacher']
(as equivalent to a view) data from the statement above to be passed to a variable, but how?
I tried this one but it shows an error
$data['schedule'] = $this->SectionsModel->getschedule($section);
foreach ($data['schedule'] as $key => $value){
echo $value['teacher'];
}
may be you can use result_array() in return value of your model.
Check your getschedule() method in your SectionModel if it's using the function result() instead of result_array().
The difference between the two methods is that result() will return object while result_array() will return array.
In you case,
$data['schedule'] = $this->SectionsModel->getschedule($section);
foreach ($data['schedule'] as $key => $value){
echo $value['teacher'];
}
Maybe $data['schedule'] is an object.You must use,
$data['schedule'] = $this->SectionsModel->getschedule($section);
foreach ($data['schedule'] as $key => $value){
echo $value->teacher;
}
If you will use result_array() method in your getschedule() in SectionModel to return result, do like this,
$data['schedule'] = $this->SectionsModel->getschedule($section);
foreach ($data['schedule'] as $key => $value){
echo $value['teacher'];
}
Hope this will help.

Laravel conditions in Controller where clause

I'm trying to build a query based on URL parameters. When the Controller is loaded I need to check which parameters have been provided and build a query from them. It's working with static values, but isn't working with conditional statements. Is my laravel syntax correct?
class OrdenesController extends BaseController {
public function showOrdenes($action)
{
$my_id = Auth::user()->id;
$my_cod = Auth::user()->codprov;
switch ($action)
{
case 'list':
$rows = DB::table('ordens')->count();
if(Input::get("jtSorting"))
{
$search = explode(" ", Input::get("jtSorting"));
$numorden= Input::get("nro_orden");
$filtros =explode(" ", $filtros);
$data = DB::table("ordens")
->select(array('*', DB::raw('SUM(cant_pend) as cant_pend'), DB::raw('SUM(importe) as importe')))
->where('cod_prov', '=', $my_cod)
->where('nro_orden', '=', $numorden)///work
---------- ////no work
if (Input::has('nro_orden')) {
->where('nro_orden', '=', $numorden)
}
---------- /// no work
->groupBy('nro_orden')
->skip(Input::get("jtStartIndex"))
->take(Input::get("jtPageSize"))
->orderBy($search[0], $search[1])
->get();
}
return Response::json(
array(
"Result" => "OK",
"TotalRecordCount" => $rows,
"Records" => $data
)
);
break;
};
}
}
You are missing the variables, no? You haven't told PHP what variable/object to do the where() to in your condition. The magic of Laravel's Eloquent (and a lot of other libraries) is that when you call its methods, it returns itself (the object) back so you can make another method call to it right away.
So when you do this:
$data = DB::table("ordens")
->select(...)
->where(...);
is the same as:
$data = DB::table("ordens");
$data = $data->select(...);
$data = $data->where(...);
But you are trying to do ->where(...) right away after if condition. You need to tell PHP which object/variable you are trying to call the method from. Like this:
$num = Input::get("nro_orden");
$data = DB::table("ordens")
->select(array('*', DB::raw('SUM(cant_pend) as cant_pend'), DB::raw('SUM(importe) as importe')))
->where('cod_prov', '=', $my_cod);
if (Input::has('nro_orden')) {
$data = $data->where('nro_orden', '=', $num);
}
$data = $data->groupBy('nro_orden')
->skip(Input::get("jtStartIndex"))
->take(Input::get("jtPageSize"))
->orderBy($search[0], $search[1])
->get();

Slim PHP and GET Parameters

I'm using Slim PHP as a framework for a RESTful API.
How do I grab GET params from the URL in Slim PHP?
For example, if I wanted to use the following:
http://api.example.com/dataset/schools?zip=99999&radius=5
You can do this very easily within the Slim framework, you can use:
$paramValue = $app->request()->params('paramName');
$app here is a Slim instance.
Or if you want to be more specific
//GET parameter
$paramValue = $app->request()->get('paramName');
//POST parameter
$paramValue = $app->request()->post('paramName');
You would use it like so in a specific route
$app->get('/route', function () use ($app) {
$paramValue = $app->request()->params('paramName');
});
You can read the documentation on the request object
http://docs.slimframework.com/request/variables/
As of Slim v3:
$app->get('/route', function ($request, $response, $args) {
$paramValue = $request->params(''); // equal to $_REQUEST
$paramValue = $request->post(''); // equal to $_POST
$paramValue = $request->get(''); // equal to $_GET
// ...
return $response;
});
For Slim 3/4 you need to use the method getQueryParams() on the PSR 7 Request object.
Citing Slim 3 / Slim 4 documentation:
You can get the query parameters as an associative array on the
Request object using getQueryParams().
I fixed my api to receive a json body OR url parameter like this.
$data = json_decode($request->getBody()) ?: $request->params();
This might not suit everyone but it worked for me.
Slim 3
$request->getQueryParam('page')
or
$app->request->getQueryParam('page')
IF YOU WANT TO GET PARAMS WITH PARAM NAME
$value = $app->request->params('key');
The params() method will first search PUT variables, then POST variables, then GET variables. If no variables are found, null is returned. If you only want to search for a specific type of variable, you can use these methods instead:
//--- GET variable
$paramValue = $app->request->get('paramName');
//--- POST variable
$paramValue = $app->request->post('paramName');
//--- PUT variable
$paramValue = $app->request->put('paramName');
IF YOU WANT TO GET ALL PARAMETERS FROM REQUEST WITHOUT SPECIFYING PARAM NAME,
YOU CAN GET ALL OF THEM INTO ARRAY IN FORMAT KEY => VALUE
$data = json_decode( $app->request->getBody() ) ?: $app->request->params();
$data will be an array that contains all fields from request as below
$data = array(
'key' => 'value',
'key' => 'value',
//...
);
Hope it helps you!
Use $id = $request->getAttribute('id'); //where id is the name of the param
In Slim 3.0 the following also works:
routes.php
require_once 'user.php';
$app->get('/user/create', '\UserController:create');
user.php
class UserController
{
public function create($request, $response, array $args)
{
$username = $request->getParam('username'));
$password = $request->getParam('password'));
// ...
}
}
Not sure much about Slim PHP, but if you want to access the parameters from a URL then you should use the:
$_SERVER['QUERY_STRING']
You'll find a bunch of blog posts on Google to solve this. You can also use the PHP function parse_url.
Inside your api controller function write the following code of line:
public function your_api_function_name(Request $request, Response $response)
{
$data = $request->getQueryParams();
$zip = $data['zip'];
$radius = $data['radius'];
}
The variable $data contains all the query parameters.
Probably obvious to most, but just in case, building on vip's answer concerning Slim 3, you can use something like the following to get the values for the parameters.
$logger = $this->getService('logger');
$params = $request->getQueryParams();
if ($params) {
foreach ($params as $key => $param) {
if (is_array($param)) {
foreach ($param as $value) {
$logger->info("param[" . $key . "] = " . $value);
}
}
else {
$logger->info("param[" . $key . "] = " . $param);
}
}
}

Categories