Building APIs at Automica HQ

Member Since 3 Years Ago

Bristol, UK

Experience Points
304,150
Total
Experience

0 experience to go until the next level!

In case you were wondering, you earn Laracasts experience when you:

  • Complete a lesson — 100pts
  • Create a forum thread — 50pts
  • Reply to a thread — 10pts
  • Leave a reply that is liked — 50pts
  • Receive a "Best Reply" award — 500pts
Lessons Completed
941
Lessons
Completed
Best Reply Awards
291
Best Reply
Awards
  • start your engines Created with Sketch.

    Start Your Engines

    Earned once you have completed your first Laracasts lesson.

  • first-thousand Created with Sketch.

    First Thousand

    Earned once you have earned your first 1000 experience points.

  • 1-year Created with Sketch.

    One Year Member

    Earned when you have been with Laracasts for 1 year.

  • 2-years Created with Sketch.

    Two Year Member

    Earned when you have been with Laracasts for 2 years.

  • 3-years Created with Sketch.

    Three Year Member

    Earned when you have been with Laracasts for 3 years.

  • 4-years Created with Sketch.

    Four Year Member

    Earned when you have been with Laracasts for 4 years.

  • 5-years Created with Sketch.

    Five Year Member

    Earned when you have been with Laracasts for 5 years.

  • school-in-session Created with Sketch.

    School In Session

    Earned when at least one Laracasts series has been fully completed.

  • welcome-newcomer Created with Sketch.

    Welcome To The Community

    Earned after your first post on the Laracasts forum.

  • full-time-student Created with Sketch.

    Full Time Learner

    Earned once 100 Laracasts lessons have been completed.

  • pay-it-forward Created with Sketch.

    Pay It Forward

    Earned once you receive your first "Best Reply" award on the Laracasts forum.

  • subscriber Created with Sketch.

    Subscriber

    Earned if you are a paying Laracasts subscriber.

  • lifer Created with Sketch.

    Lifer

    Earned if you have a lifetime subscription to Laracasts.

  • evangelist Created with Sketch.

    Laracasts Evangelist

    Earned if you share a link to Laracasts on social media. Please email [email protected] with your username and post URL to be awarded this badge.

  • chatty-cathy Created with Sketch.

    Chatty Cathy

    Earned once you have achieved 500 forum replies.

  • lara-veteran Created with Sketch.

    Laracasts Veteran

    Earned once your experience points passes 100,000.

  • 10k-strong Created with Sketch.

    Ten Thousand Strong

    Earned once your experience points hits 10,000.

  • lara-master Created with Sketch.

    Laracasts Master

    Earned once 1000 Laracasts lessons have been completed.

  • laracasts-tutor Created with Sketch.

    Laracasts Tutor

    Earned once your "Best Reply" award count is 100 or more.

  • laracasts-sensei Created with Sketch.

    Laracasts Sensei

    Earned once your experience points passes 1 million.

  • top-50 Created with Sketch.

    Top 50

    Earned once your experience points ranks in the top 50 of all Laracasts users.

  • Community Pillar

    Earned once your experience points ranks in the top 10 of all Laracasts users.

Level 50
304,150 XP
Feb
24
2 days ago
Activity icon

Awarded Best Reply on Laravel Routing: From Sub-domain To Domain Routing

@ubaid Personally, I wouldn’t even do a redirect like that within laravel, preferring to do it in a .htaccess

Redirect 301 /register http://example.com/register

This will redirect before its even span up your laravel application and so will be much quicker.

Fine to use redirectTo if you want. No need to overthink it.

Activity icon

Replied to How To Become A Professional Laravel Developer

I’ve recently started working back in laravel (after 2 years supporting a legacy client project in symfony). During my time in symfony I spent a lot of time on laracasts and worked very hard last summer with lessons and researching discussion threads to try for best answer.

That got me to level 50 but even so I am still nowhere near being completely expert in laravel (and that’s with being a commercial php developer for 20 years).

The key trigger for me levelling up as a developer wuss learning how to approach writing code from a testing perspective and for all new code to be immediately accompanied by supporting unit and functional tests.

This has also taught me to be more critical of my work but also less precious of it if someone or something better can change and improve it.

I’ve loving that I can apply the knowledge I’ve picked up by contributing to laracasts and also that It’s given me a place to freely ask questions when I’m at the edge of my knowledge.

If you work a lot on your own it’s easy to doubt your own ability (it’s known as ‘imposter syndrome’).

The best way to get more expert is to get yourself a project to build, write some tests and reassess often.

Activity icon

Replied to Wildcard Subdomain On Localhost

The second route was an example to show you how to pass in an additional argument if you needed it but have removed it as it unclear why it was there.

Does the above get you access to $subdomain inside the login route?

Activity icon

Replied to Laravel Routing: From Sub-domain To Domain Routing

@ubaid Personally, I wouldn’t even do a redirect like that within laravel, preferring to do it in a .htaccess

Redirect 301 /register http://example.com/register

This will redirect before its even span up your laravel application and so will be much quicker.

Fine to use redirectTo if you want. No need to overthink it.

Activity icon

Replied to Wildcard Subdomain On Localhost

@builtbykimster

try

Route::group(['subdomain' => '{subdomain}.localhost'], function () {

    Route::get('/login', function ($subdomain) {

		dd($subdomain);

        // 
    });
});

stolen from here: https://linuxhint.com/how-to-do-laravel-subdomain-routing/

Activity icon

Replied to No Hint Path Defined For [mail]. Laravel 7

@jayedhasan232 i'm getting the same issue.

if i use:

    public function build()
    {
        return $this
            ->markdown('emails.verifyAccount')
            ->with('mailData', $this->mailData);
    }

then my mail sends. As i have html in my templates and don't want to encode that, then i'm doing

    public function build()
    {
        return $this
            ->view('emails.verifyAccount')
            ->with('mailData', $this->mailData);
    }

which fails with @skycoder original No hint path defined for [mail]. error.

my blade looks like:

@component('mail::message')
    {{ $mailData['title'] }}

    Click link below to verify your account

    @component('mail::button', ['url' => $mailData['url']])
        Verify your account
    @endcomponent
@endcomponent

so issue seems that view is unable to understand `'mail::message'

Which is a bit weird..

@skycoder did you get yours to work using standard ->view() ?

Activity icon

Replied to Check And Count The Impression Analytics On Any Particular Post?

@yanikkumar so basically, updating a count every time the article is pulled from the db?

if that's the case, whats to stop the counter updating if someone reloads the page? also whats to stop someone DDoS your site by continually hitting the page as your site will be writing updating your record as its being rendered? 6 articles = 6 writes when you have 1 load of page.

if you are updating when the page is requested, every time a search engine indexes your site, your counters will go up, which will make the views count inaccurate at best.

Feb
23
3 days ago
Activity icon

Replied to Can't Run Tests When Using Dependency In Command

It should be avoided as you’ll have trouble testing the class.

Same reason you should avoid static methods

Activity icon

Replied to Laravel 7 Php Artisan Optimize Is Not Working

@michaloravec sadly I missed this thread and forgot to bring some popcorn.

@webstaymehr I see you have changed your username from @oxbir. I will keep an eye out for your questions.

I hope you will use this opportunity to do take stock of the advice you have been given (again). Play nice, and maybe learn something that will earn you a best answer or 2 this year and try to ‘give something back’

Bit shameful that you have only managed to watch 3 lessons though.

Activity icon

Replied to Laravel Stripe Setup

I can use cards to create tokens but for reuse, i would have to store that information, which i don't want to do.

You only need to store the token in your user table, not the card details I assume you are storing some user details?

Activity icon

Replied to Organise Routes That Return View And Json Response

I don’t see the issue with having a big routes file with its contents in groups. If your app is a SPA then I would put all routes in routes/api and use a token to authenticate the request.

If your site is a mix of standard php but with some embedded Vue components then I might stick to using just routes/web.

Your routes should be organised by resource which will make it easier to navigate through a large file.

Activity icon

Replied to Run Node Or PHP Script Stored On A Database Through An API

I’d be inclined to use a repository to store the node scripts as that would allow you to version control them. You could then use exec() to run the script within your laravel app Eg

exec("cd ". dirname($nodeJsPath). " && node nodefunc.js 2>&1", $out, $err);

See https://stackoverflow.com/questions/39505659/executing-nodejs-script-file-in-php-using-exec

Activity icon

Replied to Check And Count The Impression Analytics On Any Particular Post?

So if a page shows (perhaps? 6 articles, each article will be able to maintain its own count of when it was displayed in a page?

Would the general public see the view count or is it t being used for selling advertising?

Maybe something like hotjar would be able applied here? https://www.hotjar.com/

Activity icon

Replied to How To Run Cron Jobs For Multiple Companies

If you’ve got a list of companies that you want to a specific task for, there’s a number of ways.

Probably easiest to add a new crontab for each company and set the company_id as an argument

if you want just one crontab, for each through a list of companies and then add your current handle method inside the loop.

Depending on how long it takes to run the task, you could trigger and queue an event inside the foreach which would mean if one failed it wouldn’t kill the whole update.

Feb
22
4 days ago
Activity icon

Replied to Using {slug} For ALL Routes?

use a single table for all your pages, and add a column to store the name.the respective view. This would match a named blade file

Route::get('/{slug}', function() {

		$data = dijital::whereSlug($slug)->first();

      return view($data['template'], ['data'=>$data['content']);
});
Activity icon

Replied to Check And Count The Impression Analytics On Any Particular Post?

whats the use case then? you want to to load a view with an number of articles on it, and record which of these articles a user has read, but not clicked to load the article page on its own?

Activity icon

Replied to Using {slug} For ALL Routes?

your slug method does 2 db lookups before its even decided what view its going to load. Thats not very performant.

if you want to return a page for admin, just add:

Route::get('/admin', function() {
      return view('admin.index');
});

likewise, if you know what your slug is for About then just load the appropriate view

Route::get('/about-us', function() {
      return view('about-us');
});

and then you can use a wildcard for any other pages you can't hardcode, eg any news articles which may be being created in a db via cms

Route::get('/{slug}', function() {

		$data = dijital::whereSlug($slug)->first();

      return view('dynamic',compact('data'));
});
Feb
21
5 days ago
Activity icon

Awarded Best Reply on How To Use A Stand-alone Composer Packagist On Laravel

If you’ve got the namespace correct then you don’t need to add it again when you new up your class.

You should just be able to do:

$generate = new Generate();
Activity icon

Replied to Organise Routes That Return View And Json Response

With grouping by prefix, I probably meant something like a route for a specific role (eg /admin)

As for your naming. If you hit a route in your ajax.php via your browser (if it’s a GET) you’ll see data returned. In that case you haven’t sent an Ajax request (or used axios) so your route name doesn’t really make sense.

If you are just doing this to simply your routes file, ensure you are using route groups as this will allow you to nest your routes and will be clearer how they relate to each other.

https://laravel.com/docs/8.x/routing#route-groups

Activity icon

Replied to Run Node Or PHP Script Stored On A Database Through An API

So your laravel app is just used as a data store so you can functional test other websites?

This seems overly complicated. My understanding of functional tests is that they should live in the repo of the website you are testing, so that when you run your CI you run the tests relevant to your website. Otherwise, if functionality changes, you need to modify your script, replace the script in your laravel app to reflect the new functionality. Much easier to deploy the fix and the related functional test at the same time and that will ensure you can confirm the new functionality works before you push it out to your live environment.

Activity icon

Replied to Check And Count The Impression Analytics On Any Particular Post?

So looking to record if someone has read part of your article rather than the whole page?

Feb
20
6 days ago
Activity icon

Replied to How To Use A Stand-alone Composer Packagist On Laravel

If you’ve got the namespace correct then you don’t need to add it again when you new up your class.

You should just be able to do:

$generate = new Generate();
Activity icon

Replied to Connection Could Not Be Established With Host Mail.domain.com

Best to check with whoever supplies your email host that you have the correct port and host details.

Activity icon

Replied to Composer Update After Updating Php Version Failed?

Have you checked you have the correct versions of your packages in relation to the version of php you have updated to?

Activity icon

Replied to Run Node Or PHP Script Stored On A Database Through An API

@charrua if I’m following you correctly, you want to hit an api endpoint, execute a php script and then return the result? If that’s the case, you should look at converting your php script into a class and point your api route at it (like writing normal methods in controller).

Alternatively are you attempting to upload arbitrary files, store them in a database and then let a user execute them on your server? If so that sounds pretty risky unless you are able inspect the file and assess there’s nothing malicious in it, you put your site (and server) at risk of attack.

If you could explain why you want to be able to execute these scripts then it will be easier to recommend how.

Activity icon

Replied to How To Add A Podcast Feature In My Laravel Project?

Are you looking for a logged in user to be able attach audio files that they gave created locally and then upload to them your server? If so you could use file uploads although you could face some issues with file storage if you don’t restrict length of audio file. See https://blog.quickadminpanel.com/file-upload-in-laravel-the-ultimate-guide/

Activity icon

Awarded Best Reply on Organise Routes That Return View And Json Response

If you wish to split up your web routes to make them more manageable, then there’s no issue to create more route files specific to the type of routes you are defining. I would group by prefix rather than response type though, even if some return json and others are full blades. See https://www.itsolutionstuff.com/post/how-to-create-custom-route-file-in-laravelexample.html

I don’t recommend changing the middleware for api.php just create more web routes as you require.

Activity icon

Replied to Organise Routes That Return View And Json Response

If you wish to split up your web routes to make them more manageable, then there’s no issue to create more route files specific to the type of routes you are defining. I would group by prefix rather than response type though, even if some return json and others are full blades. See https://www.itsolutionstuff.com/post/how-to-create-custom-route-file-in-laravelexample.html

I don’t recommend changing the middleware for api.php just create more web routes as you require.

Activity icon

Replied to Spark QueryException; Subscriptions.user_id

Is this for a new install of spark?

Activity icon

Replied to Livewire Page Expired On Mobile Phone

Doesn’t seem to be an error for me on iOS with safari and chrome. Are you still getting the issue?

Feb
19
1 week ago
Activity icon

Replied to How To Create An Update Module For Laravel?

@user1980 $70 is still cheap considering how long it takes to put a decent set of course material together. I've seen 3 month courses for $10000 but what you get from that is a job with a salary in a company that will nurture you and develop your career path.

Learning is about investing in your skills. Sometimes you can do that for free, but if the resources are good then they should be valued.

I use PHPStorm for an IDE and it costs me $200 per year for the licence. I could just use VSCode or notepad but I see the value in my tooling. Using PHPStorm speeds up my development and as FT contractor this means i can bill for all my hours.

The laracasts community is an excellent way to gain knowledge and help but its formed off the back of a business model that means @jeffreyway and his team can supply excellent tutorials in exchange for a financial recompense.

If you are looking to develop your career, and be in a position where people want to buy products from you. They would expect to buying a product of a decent grade from a developer who values where they get their advice from. That person should be able to see the difference in quality between a $12 course, and a $70 course.

Feb
18
1 week ago
Activity icon

Replied to Little Error In Documentation

@vasek18 looks like you got it merged now :)

taylorotwell merged commit 5ff094f into laravel:8.x 6 hours ago

Activity icon

Replied to Laravel 7 Php Artisan Optimize Is Not Working

its part of laravel 7. But if you are getting an error you need to address what the error says to proceed.

Activity icon

Replied to How To Create An Update Module For Laravel?

I wouldn't want to buy an ecommerce product from someone who can't afford $70 for a course.

Activity icon

Replied to Best Practice For Generating Content

Echoing @snapey. If you rely on client side rendering, you could be making your content inaccessible to humans who aren't running browsers that support javascript. You may also be hiding your content from the robots (at google) who we rely on to spider our sites and make them searchable. Theres a place for sue and react but its not everywhere.

if you are new to laravel then ignore doing anything js until you have learnt the basics in php.

Activity icon

Awarded Best Reply on Laravel 7 Php Artisan Optimize Is Not Working

just run php artisan optimize:clear

Activity icon

Replied to Laravel 7 Php Artisan Optimize Is Not Working

just run php artisan optimize:clear

Activity icon

Replied to Could You Write All CSS Inside Javascript?

@martinbean I still care, having also experienced and developed for the web when it was in kbit/s..

I still feel sick inside when i see people throwing 2MB gifs in slack. You'd have paid good money for that, back in the day.

Activity icon

Replied to Laravel 7 Php Artisan Optimize Is Not Working

@oxbir why would you want to run php artisan optimize on your localhost?

Its the last place you need to optimise your codebase.

Activity icon

Replied to How Do You Structure Your Application?

Indeed. i've been contracting for ages and so have to keep abreast of PSR etc. The bulk of this site so far has been done by one dev with his boss breathing down his neck which is why we get to where we are.

Coding standards matter more when collaborating so without that its hard to decide what's best especially if you are under the lash..

Stepping in now is necessary but i've learn softly softly approach (as its better to make friends rather than bash egos)

Activity icon

Replied to How Do You Structure Your Application?

Excellent idea. I'll look into that when i've refactored my current code. This is the time (again) when i'm glad i type hint and have full code coverage.

Activity icon

Replied to How Do You Structure Your Application?

@martinbean We're only a small team at the moment but the main issue is enforcing best practice on the organisations original developers who are less savvy with best practice. I'm approaching my 'seek forgiveness' via the testing route as previously application had 0% test coverage. If you can't mock it you can't test it.

I've got a branch in PR at the moment that i can refactor to push my new code into the relevant app\Services structure which should start to enforce some guidance.

Currently i'm still fighting with explaining basics of how to name classes and getting people to add type hints and return types..

We've got a new starter coming in next week so its pretty imperative to enforce this and to establish coding standards. Fortunately agreed to follow Spatie Guidelines https://spatie.be/guidelines/laravel-php but currently it seems like only i am :P

Activity icon

Replied to How Do You Structure Your Application?

We're currently doing external calls to a API called OKTA.

These currently sit in app\Http\Helper\Okta and look like:

class LogOut
{

    /**
     * @param string $idToken
     *
     * @return string
     */
    public function handle(string $idToken): string
    {
        $response = new OktaConnection(
            'GET',
            "oauth2/v1/logout?id_token_hint=$idToken",
            $formParams = []
        );

        return $response->getCall();
    }

Because i can't mock these, i have a class at app\Http

looking like:

class LogOut
{

    /**
     * @var \App\Http\Helper\Okta\LogOut
     */
    private Helper\Okta\LogOut $logOut;

    /**
     * LogOut constructor.
     *
     * @param \App\Http\Helper\Okta\LogOut $logOut
     */
    public function __construct(Helper\Okta\LogOut $logOut)
    {
        $this->logOut = $logOut;
    }

    /**
     * @param string $token
     *
     * @return string
     * @throws \App\Exceptions\CannotFindUserException
     */
    public function handle(string $token): string
    {
        try {
            return $this->logOut->handle($token);

        } catch (Exception $exception) {

            if ($exception->getCode() == Response::HTTP_NOT_FOUND) {
                throw new CannotFindUserException($exception->getMessage());
            }
        }
    }
}

It sounds like a Services directory would be better for these. Then they could live in app\Services\Okta' and the classes in app\Http\Helper\Oktacould move toapp\Services\Okta\Api`

We're also using headless Contentful which have a number of classes related to them so could be moved to app\Services\Contentful

That shuffle might be enough at this point.

Activity icon

Started a new Conversation How Do You Structure Your Application?

I've picked up a new project which is partially built in Laravel 7 and has a small team working on it.

One thing that's bugged me is the presence of a Helper directory which seems to contain everything which isn't a model or a Controller.

We do have some single classes with static methods in them which fit the classic 'helper' pattern but along with these are classes used to call external api's, A folder full of DTOs and some other stuff which aren't either.

How would you go about unpicking this? Would we be better to move some of these up to top level with Http directory?

Any best practice links to cover any of this that i can wave to the rest of the team to enforce a bit of structure and discipline before we too lazy and continue to dump into Helper directory?

Feb
16
1 week ago
Activity icon

Replied to Mocking A Class With New'ed Up Class Inline

@tippin thanks for your response.

The purpose of this class is to allow me to DI and mock this into the controller. Previous developers were just calling the static method directly from the controller.

In my controller i am calling my ActivateUser as such:

        try {
            $validated = $this->validate($request, [
                'email_address' => 'required',
                'token' => 'required',
            ]);

            // TOKEN IS VALID or throw TokenExpiredException | DecryptException
            $validToken = $this->token->decode($validated['token']);

            // USER IS VALID or throw CannotVerifyUserException
            $user = $this->verifyUser->handle($validToken['userId']);

            // ACTIVATE ACCOUNT or throw AccountIsAlreadyVerifiedException
            $active = $this->activateUser->activate($validToken['userId']);

        } catch (TokenExpiredException $exception) {

            $data['email_address'] = $validated['email_address'];
            $data['token'] = $validated['token'];
            $data['tokenExpiry'] = (config('okta.token_expiry') / 60 / 60); // converts token expiry value to hours

            return view('account.verify', $data);

        } catch (AccountIsAlreadyActiveException $exception) {

            return redirect(route('home'))
                ->withSuccess('Account has already been verified. You can now login');

        } catch (ValidationException | DecryptException | CannotVerifyUserException $exception) {
            
            return view('account.invalidArguments');
        }

which is similar to how you are calling it.

So perhaps not injecting in the _constructor and passing the argument in within a method.

As for code above, A refactor would make like:

    /**
     * @param \Illuminate\Http\Request $request
     *
     * @return \Illuminate\Contracts\Foundation\Application|\Illuminate\Contracts\View\Factory|\Illuminate\View\View
     * @throws \Exception
     */
    public function handle(Request $request)
    {
        try {
            $validated = $this->validate($request, [
                'email_address' => 'required',
                'token' => 'required',
            ]);
        } catch (ValidationException $exception) {
            return view('account.invalidArguments');
        }

        try {
            $validToken = $this->token->decode($validated['token']);

        } catch (DecryptException $exception) {

            return view('account.invalidArguments');

        } catch (TokenExpiredException $exception) {

            $data['email_address'] = $validated['email_address'];
            $data['token'] = $validated['token'];
            $data['tokenExpiry'] = (config('okta.token_expiry') / 60 / 60); // converts token expiry value to hours

            return view('account.verify', $data);
        }

        try {
            $this->verifyUser->handle($validToken['userId']);

        } catch (CannotVerifyUserException $exception) {
            return view('account.invalidArguments');
        }

        try {
            $this->activateUser->activate($validToken['userId']);

            return redirect(route('home'))
                ->withSuccess('Account has been verified. You can now login');

        } catch (AccountIsAlreadyActiveException $exception) {
            return redirect(route('home'))
                ->withSuccess('Account has already been activated. You can now login');
        }
    }

I prefer the first way as i think its clearer (although the latter means i don't need the comments..

Activity icon

Started a new Conversation Mocking A Class With New'ed Up Class Inline

Hi All,

I'm putting in some test coverage for a laravel 7 project and have a number of classes looking like below:

<?php

namespace App\Http;

use App\Exceptions\AccountIsAlreadyActiveException;
use App\Exceptions\CannotActivateUserException;
use Exception;
use GuzzleHttp\Exception\GuzzleException;
use Illuminate\Http\Response;

/**
 * Class ActivateUser
 *
 * @package App\Http
 */
class ActivateUser
{

    /**
     * @param string $userId
     *
     * @return string
     * @throws \App\Exceptions\AccountIsAlreadyActiveException
     */
    public function activate(string $userId): string
    {
        try {
            // pass a request to external api to activate the account.
            return (new Helper\ActivateUser($userId))->activate();

        } catch (GuzzleException | Exception $exception) {

            if($exception->getCode() == Response::HTTP_FORBIDDEN) {
                throw new AccountIsAlreadyActiveException($exception->getMessage());
            }
        }
    }
}

What would the best way to approach this for testing. What i'd like to do is to Mock the response from (new Helper\ActivateUser($userId))->activate();so i can capture all the possible types of errorCode it might return.

Is this something i can do with Spies?

Feb
12
2 weeks ago
Activity icon

Awarded Best Reply on Using Markdown For The Textarea Field

@xiolog heres a good package for this

https://github.com/sinnbeck/markdom

built and maintained by our very own @sinnbeck

Activity icon

Replied to Mocked Event Fails Assertion In Laravel 7

@bugsysha thanks. Last project was for a financial services company and had all the legacy hell in it, added over 15+years. Glad to be back in laravel land. There will be more questions i promise :P

Activity icon

Replied to Mocked Event Fails Assertion In Laravel 7

@bugsysha thanks for the eyes. I was using $this->createMock method as I've been working in phpunit on symfony. The format you've used is much cleaner so i'll switch to that now.

Likewise was having limited success with $this->post passing the post params. Again, a good refactor.

Currently our store method is storing data via a 3rd party API but i've made a note to address the response code so its reflects the right error code.

Thanks for your help here. I'm back working in laravel after 2 years working on some hideous old symfony project so i've got a bit of unlearning to do :P