• Stars
    star
    481
  • Rank 91,384 (Top 2 %)
  • Language
    PHP
  • License
    MIT License
  • Created almost 6 years ago
  • Updated over 1 year ago

Reviews

There are no reviews yet. Be the first to send feedback to the community and the maintainers!

Repository Details

Generate calendars in the iCalendar format

Generate calendars in the iCalendar format

Latest Version on Packagist Tests Check & fix styling Psalm Total Downloads

Want to create online calendars so that you can display them on an iPhone's calendar app or in Google Calendar? This can be done by generating calendars in the iCalendar format (RFC 5545), a textual format that can be loaded by different applications.

The format of such calendars is defined in RFC 5545, which is not a pleasant reading experience. This package implements RFC 5545 and some extensions from RFC 7986 to provide you an easy to use API for creating calendars. It's not our intention to implement these RFC's entirely but to provide a straightforward API that's easy to use.

Here's an example of how to use it:

use Spatie\IcalendarGenerator\Components\Calendar;
use Spatie\IcalendarGenerator\Components\Event;

Calendar::create('Laracon online')
    ->event(Event::create('Creating calender feeds')
        ->startsAt(new DateTime('6 March 2019 15:00'))
        ->endsAt(new DateTime('6 March 2019 16:00'))
    )
    ->get();

The above code will generate this string:

BEGIN:VCALENDAR
VERSION:2.0
PRODID:spatie/icalendar-generator
NAME:Laracon online
X-WR-CALNAME:Laracon online
BEGIN:VEVENT
UID:5ef5c3f64cb2c
DTSTAMP;TZID=UTC:20200626T094630
SUMMARY:Creating calendar feeds
DTSTART:20190306T150000Z
DTEND:20190306T160000Z
DTSTAMP:20190419T135034Z
END:VEVENT
END:VCALENDAR

Support us

We invest a lot of resources into creating best in class open source packages. You can support us by buying one of our paid products.

We highly appreciate you sending us a postcard from your hometown, mentioning which of our package(s) you are using. You'll find our address on our contact page. We publish all received postcards on our virtual postcard wall.

Installation

You can install the package via composer:

composer require spatie/icalendar-generator

Upgrading

There were some substantial changes between v1 and v2 of the package. Check the upgrade guide for more information.

Usage

Here's how you can create a calendar:

$calendar = Calendar::create();

You can give a name to the calendar:

$calendar = Calendar::create('Laracon Online');

A description can be added to a calendar:

$calendar = Calendar::create()
    ->name('Laracon Online')
    ->description('Experience Laracon all around the world');

In the end, you want to convert your calendar to text so that it can be streamed or downloaded to the user. Here's how you do that:

Calendar::create('Laracon Online')->get(); // BEGIN:VCALENDAR ...

When streaming a calendar to an application, it is possible to set the calendar's refresh interval by duration in minutes. When setting this, the calendar application will check your server every time after the specified duration for changes to the calendar:

Calendar::create('Laracon Online')
    ->refreshInterval(5)
    ...

Event

An event can be created as follows. A name is not required, but a start date should always be given:

Event::create('Laracon Online')
    ->startsAt(new DateTime('6 march 2019'));

You can set the following properties on an event:

Event::create()
    ->name('Laracon Online')
    ->description('Experience Laracon all around the world')
    ->uniqueIdentifier('A unique identifier can be set here')
    ->createdAt(new DateTime('6 march 2019'))
    ->startsAt(new DateTime('6 march 2019 15:00'))
    ->endsAt(new DateTime('6 march 2019 16:00'));

Want to create an event quickly with a start and end date?

Event::create('Laracon Online')
    ->period(new DateTime('6 march 2019'), new DateTime('7 march 2019'));

You can add a location to an event a such:

Event::create()
    ->address('Kruikstraat 22, 2018 Antwerp, Belgium')
    ->addressName('Spatie HQ')
    ->coordinates(51.2343, 4.4287)
    ...

You can set the organizer of an event, the email address is required, but the name can be omitted:

Event::create()
    ->organizer('[email protected]', 'Ruben')
    ...

Attendees of an event can be added as such:

Event::create()
    ->attendee('[email protected]') // only an email address is required
    ->attendee('[email protected]', 'Brent')
    ...

You can also set the participation status of an attendee:

Event::create()
    ->attendee('[email protected]', 'Ruben', ParticipationStatus::accepted())
    ...

There are five participation statuses:

  • ParticipationStatus::accepted()
  • ParticipationStatus::declined()
  • ParticipationStatus::tentative()
  • ParticipationStatus::needs_action()
  • ParticipationStatus::delegated()

You can indicate that an attendee is required to RSVP to an event:

Event::create()
    ->attendee('[email protected]', 'Ruben', ParticipationStatus::needs_action(), requiresResponse: true)
    ...

An event can be made transparent, so it does not overlap visually with other events in a calendar:

Event::create()
    ->transparent()
    ...

It is possible to create an event that spans a full day:

Event::create()
    ->fullDay()
    ...

The status of an event can be set:

Event::create()
    ->status(EventStatus::cancelled())
    ...

There are three event statuses:

  • EventStatus::confirmed()
  • EventStatus::cancelled()
  • EventStatus::tentative()

An event can be classified(public, private, confidential) as such:

Event::create()
    ->classification(Classification::private())
    ...

You can add a url attachment as such:

Event::create()
    ->attachment('https://spatie.be/logo.svg')
    ->attachment('https://spatie.be/feed.xml', 'application/json')
    ...

You can add an embedded attachment (base64) as such:

Event::create()
    ->embeddedAttachment($file->toString())
    ->embeddedAttachment($fileString, 'application/json')
    ->embeddedAttachment($base64String, 'application/json', needsEncoding: false)
    ...

You can add an image as such:

Event::create()
    ->image('https://spatie.be/logo.svg')
    ->image('https://spatie.be/logo.svg', 'text/svg+xml')
    ->image('https://spatie.be/logo.svg', 'text/svg+xml', Display::badge())
    ...

There are four different image display types:

  • Display::badge()
  • Display::graphic()
  • Display::fullsize()
  • Display::thumbnail()

After creating your event, it should be added to a calendar. There are multiple options to do this:

// As a single event parameter
$event = Event::create('Creating calendar feeds');

Calendar::create('Laracon Online')
    ->event($event)
    ...

// As an array of events
Calendar::create('Laracon Online')
    ->event([
        Event::create('Creating calender feeds'),
        Event::create('Creating contact lists'),
    ])
    ...

// As a closure
Calendar::create('Laracon Online')
    ->event(function(Event $event){
        $event->name('Creating calender feeds');
    })
    ...

Using Carbon

Since this package expects a DateTimeInterface for properties related to date and time, it is possible to use the popular Carbon library:

use Carbon\Carbon;

Event::create('Laracon Online')
    ->startsAt(Carbon::now())
    ...

Timezones

Events will use the timezones defined in the DateTime objects you provide. PHP always sets these timezones in a DateTime object. By default, this will be the UTC timezone, but it is possible to change this.

Just a reminder: do not use PHP's setTimezone function on a DateTime object, it will change the time according to the timezone! It is better to create a new DateTime object with a timezone as such:

new DateTime('6 march 2019 15:00', new DateTimeZone('Europe/Brussels'))

A point can be made for omitting timezones. For example, when you want to show an event at noon in the world. We define noon at 12 o'clock, but that time is relative. It is not the same for people in Belgium, Australia, or any other country in the world.

That's why you can disable timezones on events:

$starts = new DateTime('6 march 2019 12:00')

Event::create()
    ->startsAt($starts)
    ->withoutTimezone()
    ...

You can even disable timezones for a whole calendar:

Calendar::create()
   ->withoutTimezone()
    ...

Each calendar should have Timezone components describing the timezones used within your calendar. Although not all calendar clients require this, it is recommended to add these components.

Creating such Timezone components is quite complicated. That's why this package will automatically add them for you without configuration.

You can disable this behaviour as such:

Calendar::create()
   ->withoutAutoTimezoneComponents()
    ...

You can manually add timezones to a calendar if desired as such:

$timezoneEntry = TimezoneEntry::create(
    TimezoneEntryType::daylight(),
    new DateTime('23 march 2020'),
    '+00:00',
    '+02:00'
);

$timezone = Timezone::create('Europe/Brussels')
    ->entry($timezoneEntry)
    ...

Calendar::create()
    ->timezone($timezone)
    ...

More on these timezones later.

Alerts

Alerts allow calendar clients to send reminders about specific events. For example, Apple Mail on an iPhone will send users a notification about the event. An alert always belongs to an event has a description and a number of minutes before the event it will be triggered:

Event::create('Laracon Online')
    ->alertMinutesBefore(5, 'Laracon online is going to start in five minutes');

You can also trigger an alert after the event:

Event::create('Laracon Online')
    ->alertMinutesAfter(5, 'Laracon online has ended, see you next year!');

Or trigger an alert on a specific date:

Event::create('Laracon Online')
    ->alertAt(
       new DateTime('05/16/2020 12:00:00'), 
       'Laracon online has ended, see you next year!'
    );

Removing timezones on a calendar or event will also remove timezones on the alert.

Repeating events

It is possible for events to repeat, for example your monthly company dinner. This can be done as such:

Event::create('Laracon Online')
    ->repeatOn(new DateTime('05/16/2020 12:00:00'));

And you can also repeat the event on a set of dates:

Event::create('Laracon Online')
    ->repeatOn([new DateTime('05/16/2020 12:00:00'), new DateTime('08/13/2020 15:00:00')]);

Recurrence rules

Recurrence rules or RRule's in short, make it possible to add a repeating event in your calendar by describing when it repeats within an RRule. First, we have to create an RRule:

$rrule = RRule::frequency(RecurrenceFrequency::daily());

This rule describes an event that will be repeated daily. You can also set the frequency to secondly, minutely, hourly, weekly, monthly or yearly.

The RRULE can be added to an event as such:

Event::create('Laracon Online')
    ->rrule(RRule::frequency(RecurrenceFrequency::monthly()));

It is possible to finetune the RRule to your personal taste; let's have a look!

A RRule can start from a certain point in time:

$rrule = RRule::frequency(RecurrenceFrequency::daily())->starting(new DateTime('now'));

And stop at a certain point:

$rrule = RRule::frequency(RecurrenceFrequency::daily())->until(new DateTime('now'));

It can only be repeated for a few times, 10 times for example:

$rrule = RRule::frequency(RecurrenceFrequency::daily())->times(10);

The interval of the repetition can be changed:

$rrule = RRule::frequency(RecurrenceFrequency::daily())->interval(2);

When this event starts on Monday, for example, the next repetition of this event will not occur on Tuesday but Wednesday. You can do the same for all the frequencies.

It is also possible to repeat the event on a specific weekday:

$rrule = RRule::frequency(RecurrenceFrequency::monthly())->onWeekDay(
   RecurrenceDay::friday()
);

Or on a specific weekday of a week in the month:

$rrule = RRule::frequency(RecurrenceFrequency::monthly())->onWeekDay(
   RecurrenceDay::friday(), 3
);

Or on the last weekday of a month:

$rrule = RRule::frequency(RecurrenceFrequency::monthly())->onWeekDay(
   RecurrenceDay::sunday(), -1
);

You can repeat on a specific day in the month:

$rrule = RRule::frequency(RecurrenceFrequency::monthly())->onMonthDay(16);

It is even possible to give an array of days in the month:

$rrule = RRule::frequency(RecurrenceFrequency::monthly())->onMonthDay(
   [5, 10, 15, 20]
);

Repeating can be done for certain months (for example only in the second quarter):

$rrule = RRule::frequency(RecurrenceFrequency::monthly())->onMonth(
   [RecurrenceMonth::april(), RecurrenceMonth::may(), RecurrenceMonth::june()]
);

Or just on one month only:

$rrule = RRule::frequency(RecurrenceFrequency::monthly())->onMonth(
   RecurrenceMonth::october()
);

It is possible to set the day when the week starts:

$rrule = RRule::frequency(RecurrenceFrequency::monthly())->weekStartsOn(
   ReccurenceDay::monday()
);

You can provide a specific date on which an event won't be repeated:

Event::create('Laracon Online')
    ->rrule(RRule::frequency(RecurrenceFrequency::daily()))
    ->doNotRepeatOn(new DateTime('05/16/2020 12:00:00'));

It is also possible to give an array of dates on which the event won't be repeated:

Event::create('Laracon Online')
    ->rrule(RRule::frequency(RecurrenceFrequency::daily()))
    ->doNotRepeatOn([new DateTime('05/16/2020 12:00:00'), new DateTime('08/13/2020 15:00:00')]);

Alternatively you can add RRules as a string:

Event::create('SymfonyCon')
    ->rruleAsString('FREQ=DAILY;INTERVAL=1');

If you add RRules as a string the timezones included in DTSTART and UNTIL are unknown to the package as the string is never parsed and evaluated. If they are known you can add DTSTART and UNTIL separately to help the package discover the timezones:

Event::create('SymfonyCon')
    ->rruleAsString(
        'DTSTART=20231207T090000Z;FREQ=DAILY;INTERVAL=1;UNTIL=20231208T090000Z',
        new DateTime('7 december 2023 09:00:00', new DateTimeZone('UTC')),
        new DateTime('8 december 2023 09:00:00', new DateTimeZone('UTC'))
    );

Use with Laravel

You can use Laravel Responses to stream to calendar applications:

$calendar = Calendar::create('Laracon Online');

return response($calendar->get())
    ->header('Content-Type', 'text/calendar; charset=utf-8');

If you want to add the possibility for users to download a calendar and import it into a calendar application:

$calendar = Calendar::create('Laracon Online');

return response($calendar->get(), 200, [
   'Content-Type' => 'text/calendar; charset=utf-8',
   'Content-Disposition' => 'attachment; filename="my-awesome-calendar.ics"',
]);

Crafting Timezones

If you want to craft timezone components yourself, you're in the right place, although we advise you to read the section on timezones from the RFC first.

You can create a timezone as such:

$timezone = Timezone::create('Europe/Brussels');

It is possible to provide the last modified date:

$timezone = Timezone::create('Europe/Brussels')
    ->lastModified(new DateTime('16 may 2020 12:00:00'));

Or add an url with more information about the timezone:

$timezone = Timezone::create('Europe/Brussels')
    ->url('https://spatie.be');

A timezone consists of multiple entries where the time of the timezone changed relative to UTC, such entry can be constructed for standard or daylight time:

$entry = TimezoneEntry::create(
    TimezoneEntryType::standard(), 
    new DateTime('16 may 2020 12:00:00'),
    '+00:00',
    '+02:00'
);

Firstly you provide the type of entry (standard or daylight). Then a DateTime when the time changes. Lastly, an offset relative to UTC from before the change and an offset relative to UTC after the change.

It is also possible to give this entry a name and description:

$entry = TimezoneEntry::create(...)
    ->name('Europe - Brussels')
    ->description('Belgian timezones ftw!');

An RRule for the entry can be given as such:

$entry = TimezoneEntry::create(...)
    ->rrule(RRule::frequency(RecurrenceFrequency::daily()));

In the end you can add an entry to a timezone:

$timezone = Timezone::create('Europe/Brussels')
   ->entry($timezoneEntry);

Or even add multiple entries:

$timezone = Timezone::create('Europe/Brussels')
   ->entry([$timezoneEntryOne, $timezoneEntryTwo]);

Now we've constructed our timezone it is time(๐Ÿ‘€) to add this timezone to our calendar:

$calendar = Calendar::create('Calendar with timezones')
   ->timezone($timezone);

It is also possible to add multiple timezones:

$calendar = Calendar::create('Calendar with timezones')
   ->timezone([$timezoneOne, $timezoneTwo]);

Extending the package

We try to keep this package as straightforward as possible. That's why a lot of properties and subcomponents from the RFC are not included in this package. We've made it possible to add other properties or subcomponents to each component if you might need something not included in the package. But be careful! From this moment, you're on your own correctly implementing the RFC's.

Appending properties

You can add a new property to a component like this:

Calendar::create()
    ->appendProperty(
        TextProperty::create('ORGANIZER', '[email protected]')
    )
    ...

Here we've added a TextProperty , and this is a default key-value property type with a text as value. You can also use one of the default properties included in the package or create your own by extending the Property class.

Sometimes a property can have some additional parameters, these are key-value entries and can be added to properties as such:

$property = TextProperty::create('ORGANIZER', '[email protected]')
    ->addParameter(Parameter::create('CN', 'RUBEN VAN ASSCHE'));

Calendar::create()
    ->appendProperty($property)
    ...

Appending subcomponents

A subcomponent can be appended as such:

Calendar::create()
    ->appendSubComponent(
        Event::create('Extending icalendar-generator')
    )
    ...

It is possible to create your subcomponents by extending the Component class.

Testing

composer test

Alternatives

We strive for a simple and easy to use API. Want something more? Then check out this package by Markus Poerschke.

Changelog

Please see CHANGELOG for more information on what has changed recently.

Contributing

Please see CONTRIBUTING for details.

Security

If you've found a bug regarding security please mail [email protected] instead of using the issue tracker.

Postcardware

You're free to use this package, but if it makes it to your production environment we highly appreciate you sending us a postcard from your hometown, mentioning which of our package(s) you are using.

Our address is: Spatie, Kruikstraat 22, box 12, 2018 Antwerp, Belgium.

We publish all received postcards on our company website.

Credits

License

The MIT License (MIT). Please see License File for more information.

More Repositories

1

laravel-permission

Associate users with roles and permissions
PHP
11,600
star
2

laravel-medialibrary

Associate files with Eloquent models
PHP
5,427
star
3

laravel-backup

A package to backup your Laravel app
PHP
5,337
star
4

laravel-activitylog

Log activity inside your Laravel app
PHP
5,316
star
5

browsershot

Convert HTML to an image, PDF or string
PHP
4,434
star
6

laravel-query-builder

Easily build Eloquent queries from API requests
PHP
3,675
star
7

laravel-analytics

A Laravel package to retrieve pageviews and other data from Google Analytics
PHP
2,948
star
8

image-optimizer

Easily optimize images using PHP
PHP
2,450
star
9

async

Easily run code asynchronously
PHP
2,401
star
10

crawler

An easy to use, powerful crawler implemented in PHP. Can execute Javascript.
PHP
2,400
star
11

laravel-responsecache

Speed up a Laravel app by caching the entire response
PHP
2,248
star
12

data-transfer-object

Data transfer objects with batteries included
PHP
2,220
star
13

laravel-translatable

Making Eloquent models translatable
PHP
2,030
star
14

laravel-sitemap

Create and generate sitemaps with ease
PHP
2,011
star
15

dashboard.spatie.be

The source code of dashboard.spatie.be
PHP
1,940
star
16

laravel-fractal

An easy to use Fractal wrapper built for Laravel and Lumen applications
PHP
1,845
star
17

package-skeleton-laravel

A skeleton repository for Spatie's Laravel Packages
PHP
1,714
star
18

period

Complex period comparisons
PHP
1,618
star
19

laravel-collection-macros

A set of useful Laravel collection macros
PHP
1,602
star
20

laravel-newsletter

Manage Mailcoach and MailChimp newsletters in Laravel
PHP
1,570
star
21

checklist-going-live

The checklist that is used when a project is going live
1,489
star
22

laravel-tags

Add tags and taggable behaviour to your Laravel app
PHP
1,454
star
23

opening-hours

Query and format a set of opening hours
PHP
1,340
star
24

schema-org

A fluent builder Schema.org types and ld+json generator
PHP
1,337
star
25

eloquent-sortable

Sortable behaviour for Eloquent models
PHP
1,268
star
26

laravel-cookie-consent

Make your Laravel app comply with the crazy EU cookie law
PHP
1,268
star
27

laravel-data

Powerful data objects for Laravel
PHP
1,240
star
28

laravel-sluggable

An opinionated package to create slugs for Eloquent models
PHP
1,236
star
29

laravel-settings

Store strongly typed application settings
PHP
1,218
star
30

laravel-searchable

Pragmatically search through models and other sources
PHP
1,217
star
31

pdf-to-image

Convert a pdf to an image
PHP
1,207
star
32

laravel-mail-preview

A mail driver to quickly preview mail
PHP
1,171
star
33

once

A magic memoization function
PHP
1,159
star
34

laravel-honeypot

Preventing spam submitted through forms
PHP
1,134
star
35

laravel-image-optimizer

Optimize images in your Laravel app
PHP
1,121
star
36

laravel-google-calendar

Manage events on a Google Calendar
PHP
1,119
star
37

regex

A sane interface for php's built in preg_* functions
PHP
1,097
star
38

laravel-multitenancy

Make your Laravel app usable by multiple tenants
PHP
1,092
star
39

image

Manipulate images with an expressive API
PHP
1,064
star
40

array-to-xml

A simple class to convert an array to xml
PHP
1,056
star
41

laravel-uptime-monitor

A powerful and easy to configure uptime and ssl monitor
PHP
1,020
star
42

db-dumper

Dump the contents of a database
PHP
987
star
43

laravel-webhook-client

Receive webhooks in Laravel apps
PHP
985
star
44

laravel-model-states

State support for models
PHP
968
star
45

laravel-view-models

View models in Laravel
PHP
963
star
46

simple-excel

Read and write simple Excel and CSV files
PHP
930
star
47

laravel-web-tinker

Tinker in your browser
JavaScript
925
star
48

laravel-webhook-server

Send webhooks from Laravel apps
PHP
920
star
49

calendar-links

Generate add to calendar links for Google, iCal and other calendar systems
PHP
904
star
50

laravel-db-snapshots

Quickly dump and load databases
PHP
889
star
51

laravel-mix-purgecss

Zero-config Purgecss for Laravel Mix
JavaScript
887
star
52

laravel-schemaless-attributes

Add schemaless attributes to Eloquent models
PHP
880
star
53

blender

The Laravel template used for our CMS like projects
PHP
879
star
54

fork

A lightweight solution for running code concurrently in PHP
PHP
863
star
55

laravel-schedule-monitor

Monitor scheduled tasks in a Laravel app
PHP
859
star
56

laravel-menu

Html menu generator for Laravel
PHP
854
star
57

phpunit-watcher

A tool to automatically rerun PHPUnit tests when source code changes
PHP
831
star
58

laravel-failed-job-monitor

Get notified when a queued job fails
PHP
826
star
59

laravel-model-status

Easily add statuses to your models
PHP
818
star
60

form-backend-validation

An easy way to validate forms using back end logic
JavaScript
800
star
61

temporary-directory

A simple class to work with a temporary directory
PHP
796
star
62

laravel-feed

Easily generate RSS feeds
PHP
789
star
63

laravel-event-sourcing

The easiest way to get started with event sourcing in Laravel
PHP
772
star
64

enum

Strongly typed enums in PHP supporting autocompletion and refactoring
PHP
769
star
65

laravel-server-monitor

Don't let your servers just melt down
PHP
769
star
66

laravel-package-tools

Tools for creating Laravel packages
PHP
767
star
67

laravel-tail

An artisan command to tail your application logs
PHP
726
star
68

valuestore

Easily store some values
PHP
722
star
69

laravel-health

Check the health of your Laravel app
PHP
719
star
70

geocoder

Geocode addresses to coordinates
PHP
709
star
71

pdf-to-text

Extract text from a pdf
PHP
707
star
72

ssh

A lightweight package to execute commands over an SSH connection
PHP
696
star
73

menu

Html menu generator
PHP
688
star
74

laravel-url-signer

Create and validate signed URLs with a limited lifetime
PHP
685
star
75

ssl-certificate

A class to validate SSL certificates
PHP
675
star
76

laravel-route-attributes

Use PHP 8 attributes to register routes in a Laravel app
PHP
674
star
77

laravel-validation-rules

A set of useful Laravel validation rules
PHP
663
star
78

laravel-pdf

Create PDF files in Laravel apps
PHP
661
star
79

url

Parse, build and manipulate URL's
PHP
659
star
80

laravel-html

Painless html generation
PHP
654
star
81

laravel-event-projector

Event sourcing for Artisans ๐Ÿ“ฝ
PHP
642
star
82

laravel-server-side-rendering

Server side rendering JavaScript in your Laravel application
PHP
636
star
83

vue-tabs-component

An easy way to display tabs with Vue
JavaScript
626
star
84

macroable

A trait to dynamically add methods to a class
PHP
621
star
85

laravel-blade-javascript

A Blade directive to export variables to JavaScript
PHP
618
star
86

laravel-onboard

A Laravel package to help track user onboarding steps
PHP
616
star
87

laravel-csp

Set content security policy headers in a Laravel app
PHP
614
star
88

laravel-cors

Send CORS headers in a Laravel application
PHP
607
star
89

laravel-short-schedule

Schedule artisan commands to run at a sub-minute frequency
PHP
607
star
90

laravel-translation-loader

Store your translations in the database or other sources
PHP
602
star
91

vue-table-component

A straight to the point Vue component to display tables
JavaScript
591
star
92

activitylog

A very simple activity logger to monitor the users of your website or application
PHP
586
star
93

phpunit-snapshot-assertions

A way to test without writing actual testย cases
PHP
584
star
94

http-status-check

CLI tool to crawl a website and check HTTP status codes
PHP
584
star
95

laravel-queueable-action

Queueable actions in Laravel
PHP
584
star
96

ray

Debug with Ray to fix problems faster
PHP
574
star
97

freek.dev

The sourcecode of freek.dev
PHP
571
star
98

server-side-rendering

Server side rendering JavaScript in a PHP application
PHP
568
star
99

string

String handling evolved
PHP
558
star
100

laravel-http-logger

Log HTTP requests in Laravel applications
PHP
538
star