proc_open() fork fails in Laravel controller - laravel

I get an error saying: proc_open(): fork failed - Cannot allocate memory in a Laravel controller. The generate function is called with axios (Vuejs SAP).
This is what my controller looks like
use Illuminate\Http\Request;
use Illuminate\Http\UploadedFile;
use Illuminate\Support\Facades\Storage;
use GifCreator\AnimGif;
use simpleimage\SimpleImage;
use Symfony\Component\Process\Process;
use Symfony\Component\Process\Exception\ProcessFailedException;
class GifController extends Controller
{
//
public function generate(Request $request)
{
if(!$request->ajax()) return;
$cmd = 'ls';
$process = new Process($cmd);
$process->run();
// executes after the command finishes
if (!$process->isSuccessful()) {
throw new ProcessFailedException($process);
}
echo $process->getOutput();
}
}
free -m on server:
| | total | used | free | shared | buff/cache | available |
| ----- | ------ | ----- | ---- | ------ | ---------- | --------- |
| Mem: | 2000 | 243 | 577 | 20 | 1178 | 1541 |
| Swap: | 4095 | 0 | 4095 | | | |
EDIT:
As Hilmi pointed out I've now tried adding a swap space, and now the command runs successfully sometimes – about half of the time.
Is there a way to retry the Process if it fails?

Related

Laravel | Return rows in order based off pivot

I have the following setup:
stages:
| id | name | order |
commands:
| id | name | body |
------------------------------=
| 1 | test | phpunit |
| 2 | style | echo "style" |
| 3 | deploy | deploy |
command_stage:
| command_id | stage_id | order |
---------------------------------
| 1 | 1 | 1 |
| 2 | 2 | 1 |
| 3 | 1 | 2 |
Basically, I would like to create a method on the stage model which allows me to get all of the commands back based off of the order, but commands have a specific order and so do the stages.
So each command is stored under a stage so we know which part to run but each command also has an order in that stage. Now I know I can do something like the following:
$inOrder = collect();
Stage::get()->each(function ($stage) {
$commands = $stage->commands()->orderByPivot('order')->get();
$inOrder->push($commands);
});
return $inOrder;
But I was wondering if there is a nicer way to do this? Or even a way to do this solely on one database hit?
Pre-load and sort the relationship:
$stages = Stage::with(['commands' => function ($subQuery) {
$subQuery->orderBy('command_stage', 'order');
}])->get();
foreach($stages as $stage) {
$inOrder->push($stage->commands);
}
This method of Eager-Loading will reduce the N+1 query issue of doing $stage->commands() inside the foreach() loop.

SOLVED Laravel website returns "Error 404" for GET requests

So I got a template of a Flutter app that retrieves all its data from a website using HTTP get requests.
I have the following method that gets the list of resturaunts:
Future<Stream<Restaurant>> getNearRestaurants(LocationData myLocation, LocationData areaLocation) async {
String _nearParams = '';
String _orderLimitParam = '';
if (myLocation != null && areaLocation != null) {
_orderLimitParam = 'orderBy=area&limit=5';
_nearParams = '&myLon=${myLocation.longitude}&myLat=${myLocation.latitude}&areaLon=${areaLocation.longitude}&areaLat=${areaLocation.latitude}';
}
final String url = '${GlobalConfiguration().getString('api_base_url')}restaurants?$_nearParams&$_orderLimitParam';
final client = new http.Client();
final streamedRest = await client.send(http.Request('get', Uri.parse(url)));
return streamedRest.stream.transform(utf8.decoder).transform(json.decoder).map((data) => Helper.getData(data)).expand((data) => (data as List)).map((data) {
return Restaurant.fromJSON(data);
});
}
However when I swap the template's url variable for my own website, the app gets stuck and streamRest returns with an error 404 page.
Tried Solutions:
I surrounded it with a try/catch block and it gave me no exceptions.
I also installed postman and checked my website with the GET statement for the same list of restaurants I try to retrieve in the flutter code posted above and see this: Postman GET screenshot
Its as if my website cannot route to the specific pages in my API folder. But they are all defined in api.php.
Update 1:
My web.php looks like this https://pastebin.com/QRG300uL. It seems to be similar to what was suggested below
Update 2:
I ran php artisan route::list and it showed that all the routes seem to be there:
| | POST | api/restaurant_reviews | restaurant_reviews.store | App\Http\Controllers\API\RestaurantReviewAPIController#store | api |
| | GET|HEAD | api/restaurant_reviews | restaurant_reviews.index | App\Http\Controllers\API\RestaurantReviewAPIController#index | api |
| | GET|HEAD | api/restaurant_reviews/create | restaurant_reviews.create | App\Http\Controllers\API\RestaurantReviewAPIController#create | api |
| | DELETE | api/restaurant_reviews/{restaurant_review} | restaurant_reviews.destroy | App\Http\Controllers\API\RestaurantReviewAPIController#destroy | api |
| | GET|HEAD | api/restaurant_reviews/{restaurant_review} | restaurant_reviews.show | App\Http\Controllers\API\RestaurantReviewAPIController#show | api |
| | PUT|PATCH | api/restaurant_reviews/{restaurant_review} | restaurant_reviews.update | App\Http\Controllers\API\RestaurantReviewAPIController#update | api |
| | GET|HEAD | api/restaurant_reviews/{restaurant_review}/edit | restaurant_reviews.edit | App\Http\Controllers\API\RestaurantReviewAPIController#edit | api |
| | GET|HEAD | api/restaurants | restaurants.index | App\Http\Controllers\API\RestaurantAPIController#index | api |
| | POST | api/restaurants | restaurants.store | App\Http\Controllers\API\RestaurantAPIController#store | api |
| | GET|HEAD | api/restaurants/create | restaurants.create | App\Http\Controllers\API\RestaurantAPIController#create | api |
| | GET|HEAD | api/restaurants/{restaurant} | restaurants.show | App\Http\Controllers\API\RestaurantAPIController#show | api |
| | DELETE | api/restaurants/{restaurant} | restaurants.destroy | App\Http\Controllers\API\RestaurantAPIController#destroy | api |
| | PUT|PATCH | api/restaurants/{restaurant} | restaurants.update | App\Http\Controllers\API\RestaurantAPIController#update | api |
| | GET|HEAD | api/restaurants/{restaurant}/edit | restaurants.edit | App\Http\Controllers\API\RestaurantAPIController#edit | api |
| | POST | api/send_reset_link_email | | App\Http\Controllers\API\UserAPIController#sendResetLinkEmail | api |
| | GET|HEAD | api/settings | | App\Http\Controllers\API\UserAPIController#settings | api |
Solution:
This worked for me after changing alot of things, I changed my GET request url from "www.domain.com/api/resturants" to "www.domain.com/public/api/resturants"
Well i don't know about your flutter code for i use different methods in retrieving data from api but about the routes i suggest you do like me
in web.php the route file
//Api routes
Route::get('/company/api/fetch', 'ApiController#fetch_companies');
my api controller
public function fetch_companies()
{
$companies = Companies::all();
return response()->json($companies);
}
this way you will get the data passed to the route /company/api/fetch (you can modify that as you want) and when a get request enter this page it will return json
and for the request handling in flutter side i suggest you make your functions and classes as it is in the documentations
Note: that the flutter solution that i suggested may not work with your case for you are using Stream which is different than this type of requests because this type runs only ones while the Stream runs many times and gets data every time it gets new data from the server

Laravel - How to run schedule in multiple packages

currently, i'm working with project that has some modules which need to run schedule job.
I want to take schedule job into Kernel of each module (not Kernel in app/Console directory).
I did like this Laravel 5 Package Scheduled Tasks but it only run on 1 module. The others did not run.
Can anybody please help me! Thanks
My source code has structure like this:
app
| Console
| | Commands
| | | Command.php
| | Kernel.php
bootstrap
...
Module
| Module 1
| | Console
| | | Commands
| | | | Command11.php
| | | | Command12.php
| | | Kernel.php
| Module 2
| | Console
| | | Commands
| | | | Command21.php
| | | | Command22.php
| | | Kernel.php

Use a non-unique route key name?

We have rows which are sequenced and scoped to each organisation. So:
Processes tbl:
| id | org_id | sequence | name |
|---- |-------- |---------- |------------------- |
| 23 | 1 | 1 | New person |
| 56 | 1 | 2 | Person leaves |
| 84 | 1 | 3 | Person absent |
| 26 | 2 | 1 | Something happens |
| 34 | 2 | 2 | Something else |
| 77 | 2 | 3 | And another |
We do this so they can have a simple numbering system for their own records rather than a UUID, hash or something else. We prefer to have this in the url as well, so:
example.com/processes/1
Once logged in, we know their org_id, so for each query we can use org_id along with the sequence from the url.
Is there a clean laravel-esque kind of way to achieve this, maybe using the Model's getRouteKeyName?
I got the answer with some help from the laracasts forum:
/**
* Retrieve the model for a bound value.
*
* #param mixed $value
* #return \Illuminate\Database\Eloquent\Model|null
*/
public function resolveRouteBinding($value)
{
return $this->where('sequence', $value)
->where('org_id', /* however you get your org_id */)
->first() ?? abort(404);
}

How can I compare against FileSystemRights using Powershell?

I want to check whether a given user has access to a given folder - by checking if they have "Modify" access assigned to them.
I thought that the PS for that would be:
(Get-Acl .\myfolder).Access | ?{$_.IdentityReference -eq "BUILTIN\Users"} |?{$_.filesystemrights.value -contains "Modify"}
But the final part of that isn't working - I get back no result. But I know that they have Modify access - if I put in:
(Get-Acl .\myfolder).Access | ?{$_.IdentityReference -eq "BUILTIN\Users"} | select -ExpandProperty filesystemrights
then I get back:
Modify, Synchronize
ReadAndExecute, Synchronize
Is this because the FileSystemRights property is an enumeration? And if so, how do I test against it?
It's a type problem. (Get-Acl .\myfolder).Access[].FileSystemRights is of type System.Security.AccessControl.FileSystemRights. It's not really displaying a string. To make it a string, just use the ToString() method:
(Get-Acl .\myfolder).Access | ?{$_.IdentityReference -eq "BUILTIN\Users"} |?{$_.filesystemrights.ToString() -contains "Modify"}
Or you can use the bitwise comparison method. However, it's very easy to confuse when you want to use this:
($_.FileSystemRights -band [System.Security.AccessControl.FileSystemRights]::Modify) -eq [System.Security.AccessControl.FileSystemRights]::Modify
With when you want to use this:
($_.FileSystemRights -band [System.Security.AccessControl.FileSystemRights]::Modify) -eq $_.FileSystemRights
They have very different meanings. For example, if you have Full Control, the former test is still true. Is that what you want? Or do you want to know when the FileSystemRights are literally just Modify?
Also, [System.Security.AccessControl.FileSystemRights] is an incomplete enumeration. In my environment, I found I needed this table:
+-------------+------------------------------+------------------------------+
| Value | Name | Alias |
+-------------+------------------------------+------------------------------+
| -2147483648 | GENERIC_READ | GENERIC_READ |
| 1 | ReadData | ListDirectory |
| 1 | ReadData | ReadData |
| 2 | CreateFiles | CreateFiles |
| 2 | CreateFiles | WriteData |
| 4 | AppendData | AppendData |
| 4 | AppendData | CreateDirectories |
| 8 | ReadExtendedAttributes | ReadExtendedAttributes |
| 16 | WriteExtendedAttributes | WriteExtendedAttributes |
| 32 | ExecuteFile | ExecuteFile |
| 32 | ExecuteFile | Traverse |
| 64 | DeleteSubdirectoriesAndFiles | DeleteSubdirectoriesAndFiles |
| 128 | ReadAttributes | ReadAttributes |
| 256 | WriteAttributes | WriteAttributes |
| 278 | Write | Write |
| 65536 | Delete | Delete |
| 131072 | ReadPermissions | ReadPermissions |
| 131209 | Read | Read |
| 131241 | ReadAndExecute | ReadAndExecute |
| 197055 | Modify | Modify |
| 262144 | ChangePermissions | ChangePermissions |
| 524288 | TakeOwnership | TakeOwnership |
| 1048576 | Synchronize | Synchronize |
| 2032127 | FullControl | FullControl |
| 268435456 | GENERIC_ALL | GENERIC_ALL |
| 536870912 | GENERIC_EXECUTE | GENERIC_EXECUTE |
| 1073741824 | GENERIC_WRITE | GENERIC_WRITE |
+-------------+------------------------------+------------------------------+
It's interesting to compare the output of these:
[System.Enum]::GetNames([System.Security.AccessControl.FileSystemRights]);
[System.Enum]::GetNames([System.Security.AccessControl.FileSystemRights]) | % { "$($_.ToString())`t`t$([System.Security.AccessControl.FileSystemRights]$_.ToString())`t`t$(([System.Security.AccessControl.FileSystemRights]$_).value__)";}
[System.Enum]::GetValues([System.Security.AccessControl.FileSystemRights]) | % { "$($_.ToString())`t`t$(($_).value__)";}
The GENERIC rights are not enumerated in the .Net class, but you will see that numeric value if you enumerate enough files.
Good luck!
Got it:
(get-acl .\myfolder).Access | ?{$_.IdentityReference -eq "BUILTIN\Users"} | ?{($_.FileSystemRights -band [System.Security.AccessControl.FileSystemRights]::Modify) -eq [System.Security.AccessControl.FileSystemRights]::Modify}
It's both a bitwise comparison - and therefore you need to use "-band".
But "-band" will return true if any of the same bits are set in both enumerations. And as even "Read" has several bits set (it's 100000000010001001) - some of which will match with "Modify", you need to also compare the result with "Modify" to make sure that the result is actually the same.
(Thanks to the comments below for getting me pointed in the right direction.)
Updated new version.
Clarified version from Arco's comment.
With this version we're checking if the Modify bit is set.
(Get-Acl .\myfolder).Access | ?{$_.IdentityReference -eq "BUILTIN\Users"} |?{ $_.FileSystemRights -band [Security.AccessControl.FileSystemRights]::Modify}
The value__ property is the numeric bit set version.

Resources