A fluent extension to PHPs DateTime class.

Overview

Expressive Date

A fluent extension to PHPs DateTime class.

Build Status

Table of Contents

Installation

Composer

Add Expressive Date to your composer.json file.

"jasonlewis/expressive-date": "1.0.*"

Run composer install to get the latest version of the package.

Manually

It's recommended that you use Composer, however you can download and install from this repository.

Laravel 4

Expressive Date comes with a service provider for Laravel 4. You'll need to add it to your composer.json as mentioned in the above steps, then register the service provider with your application.

Open app/config/app.php and find the providers key. Add ExpressiveDateServiceProvider to the array.

You can get an instance of Expressive Date through the applications container.

$date = App::make('date');

// Or if you have access to an instance of the application.
$date = $app['date'];

You can also use the other instantiation methods described below.

Usage

Expressive Date is an extension to PHPs DateTime class. This means that if you can't do something with Expressive Date you still have the flexibility of DateTime at your disposal.

Getting Instances

Before you can begin working with dates you'll need to get an instance of ExpressiveDate. You have a number of options available to you.

// Instantiate a new instance of Expressive Date.
// This will create an instance and use the current date and time
$date = new ExpressiveDate;

// Use the static make method to get an instance of Expressive Date.
$date = ExpressiveDate::make();

Both of these methods accepts two parameters, a time string and a timezone. This is identical to the DateTime constructor except the second parameters timezone does not need to be an intance of DateTimeZone.

// Pass a valid timezone as the second parameter.
$date = new ExpressiveDate(null, 'Australia/Melbourne');

// Or you can still use a DateTimeZone instance.
$timezone = new DateTimeZone('Australia/Melbourne');

$date = new ExpressiveDate(null, $timezone);

Alternatively, you can make a date from existing dates or times.

// You can use existing dates to get an instance of Expressive Date.
$date = ExpressiveDate::makeFromDate(2012, 1, 31);

// If you have the time, you can use that instead.
$date = ExpressiveDate::makeFromTime(14, 30, 0);

If you use null as any of the parameters then Expressive Date will use the current respective value. The only exception to this is if you supply an hour to ExpressiveDate::makeFromTime() but no minute or second, instead of defaulting to the current minute or second it will set them to 0. This mimicks the existing functionality when interacting with dates using PHP.

Quick Helpers

There are a couple of quick helper methods available to you when using Expressive Date.

$date = new ExpressiveDate; // Creates an instance that uses current date and time

$date->today(); // Sets to todays date, e.g., 1991-01-31 00:00:00

$date->tomorrow(); // Sets to tomorrows date, e.g., 1991-02-01 00:00:00

$date->yesterday(); // Sets to yesterdays date, e.g., 1991-01-30 00:00:00

These helpers also set the time to midnight.

Cloning

You can clone an instance of ExpressiveDate with the clone() method.

$date = new ExpressiveDate;

$clone = $date->clone();

A clone is identical to the original instance and is useful when you need to compare or manipulate a date without affecting the original instance.

Manipulating Dates

When working with dates you'll often want to manipulate it in a number of ways. Expressive Date eases this process with a simple and intuitive syntax.

$date = new ExpressiveDate('December 1, 2012 12:00:00 PM');

$date->addOneDay(); // December 2, 2012 12:00:00 PM
$date->addDays(10); // December 12, 2012 12:00:00 PM
$date->minusOneDay(); // December 11, 2012 12:00:00 PM
$date->minusDays(10); // December 1, 2012 12:00:00 PM

$date->addOneWeek(); // December 8, 2012 12:00:00 PM
$date->addWeeks(10); // February 16, 2013, at 12:00:00 PM
$date->minusOneWeek(); // February 9, 2013 12:00:00 PM
$date->minusWeeks(10); // December 1, 2012 12:00:00 PM

$date->addOneMonth(); // January 1, 2013 12:00:00 PM
$date->addMonths(10); // November 1, 2013 12:00:00 PM
$date->minusOneMonth(); // October 1, 2013 12:00:00 PM
$date->minusMonths(10); // December 1, 2012 12:00:00 PM

$date->addOneYear(); // December 1, 2013 12:00:00 PM
$date->addYears(10); // December 1, 2023 12:00:00 PM
$date->minusOneYear(); // December 1, 2022 12:00:00 PM
$date->minusYears(10); // December 1, 2012 12:00:00 PM

$date->addOneHour(); // December 1, 2012 1:00:00 PM
$date->addHours(10); // December 1, 2012 11:00:00 PM
$date->minusOneHour(); // December 1, 2012 10:00:00 PM
$date->minusHours(10); // December 1, 2012 12:00:00 PM

$date->addOneMinute(); // December 1, 2012 12:01:00 PM
$date->addMinutes(10); // December 1, 2012 12:11:00 PM
$date->minusOneMinute(); // December 1, 2012 12:10:00 PM
$date->minusMinutes(10); // December 1, 2012 12:00:00 PM

$date->addOneSecond(); // December 1, 2012 12:00:01 PM
$date->addSeconds(10); // December 1, 2012 12:00:11 PM
$date->minusOneSecond(); // December 1, 2012 12:00:10 PM
$date->minusSeconds(10); // December 1, 2012 12:00:00 PM

You can also set the unit manually using one of the setters.

$date = new ExpressiveDate('December 1, 2012 12:00:00 PM');

$date->setDay(31); // December 31, 2012 12:00:00 PM
$date->setMonth(1); // January 31, 2012 12:00:00 PM
$date->setYear(1991); // January 31, 1991 12:00:00 PM
$date->setHour(6); // January 31, 1991 6:00:00 AM
$date->setMinute(30); // January 31, 1991 6:30:00 AM
$date->setSecond(53); // January 31, 1991 6:30:53 AM

There are also several methods to quick jump to the start or end of a day, month, or week.

$date = new ExpressiveDate('December 1, 2012 12:00:00 PM');

$date->startOfDay(); // December 1, 2012 12:00:00 AM
$date->endOfDay(); // December 1, 2012 11:59:59 PM

$date->startOfWeek(); // 25th November, 2012 at 12:00 AM
$date->endOfWeek(); // 1st December, 2012 at 11:59 PM

$date->startOfMonth(); // December 1, 2012 12:00:00 AM
$date->endOfMonth(); // December 31, 2012 11:59:59 PM

The start and end of the week are influenced by what day you configure to be the start of the week. In America, the start of the week is Sunday and for most other places it's Monday. By default the start of the week is Sunday.

$date = new ExpressiveDate('December 1, 2012 12:00:00 PM');

// Set the week start day to Monday, to set it to Sunday you'd use 0.
$date->setWeekStartDay(1);

// You can also use the actual name of the day so it makes more sense.
$date->setWeekStartDay('monday');

$date->startOfWeek(); // 26th November, 2012 at 12:00 AM

Lastly you can set the timestamp directly or set it from a string.

$date = new ExpressiveDate;

$date->setTimestamp(time()); // Set the timestamp to the current time.
$date->setTimestampFromString('31 January 1991'); // Set timestamp from a string.

Differences Between Dates

Getting the difference between two dates is very easy with Expressive Date. Let's see how long it's been since my birthday, which was on the 31st January, 1991.

$date = new ExpressiveDate('January 31, 1991');
$now = new ExpressiveDate('December 1, 2012');

$date->getDifferenceInYears($now); // 21
$date->getDifferenceInMonths($now); // 262
$date->getDifferenceInDays($now); // 7975
$date->getDifferenceInHours($now); // 191400
$date->getDifferenceInMinutes($now); // 11484000
$date->getDifferenceInSeconds($now); // 689040000

Wow, I'm over 689040000 seconds old!

In the above example I'm explicitly passing in another instance to compare against. You don't have to, by default it'll use the current date and time.

$date = new ExpressiveDate('January 31, 1991');

$date->getDifferenceInYears(); // Will use the current date and time to get the difference.

Comparing Dates

Being able to compare two dates is important in many applications. Expressive Date allows you to compare two ExpressiveDate instances against one another in a variety of ways.

$date = new ExpressiveDate;

$date->equalTo($date->clone()); // true
$date->sameAs($date->clone()->minusOneDay()); // false
$date->notEqualTo($date->clone()); // false
$date->greaterThan($date->clone()->minusOneDay()); // true
$date->lessThan($date->clone()->addOneDay()); // true
$date->greaterOrEqualTo($date->clone()); // true
$date->lessOrEqualTo($date->clone()->minusOneDay()); // false

The methods themselves should be self explanatory. The sameAs() method is an alias of equalTo().

Interacting With Dates

Expressive Date provides a number of helpful methods for interacting with your dates and times.

$date = new ExpressiveDate('December 1, 2012 2:30:50 PM');

$date->getDay(); // 1
$date->getMonth(); // 12
$date->getYear(); // 2012
$date->getHour(); // 14
$date->getMinute(); // 30
$date->getSecond(); // 50
$date->getDayOfWeek(); // Saturday
$date->getDayOfWeekAsNumeric(); // 6
$date->getDaysInMonth(); // 31
$date->getDayOfYear(); // 335
$date->getDaySuffix(); // st
$date->getGmtDifference(); // +1100
$date->getSecondsSinceEpoch(); // 1354320000
$date->isLeapYear(); // true
$date->isAmOrPm(); // PM
$date->isDaylightSavings(); // true
$date->isWeekday(); // false
$date->isWeekend(); // true

Formatting Dates

It's now time to display your date and time to everyone. Expressive Date comes with a couple of predefined formatting methods for your convenience.

$date = new ExpressiveDate('December 1, 2012 2:30:50 PM');

$date->getDate(); // 2012-12-01
$date->getDateTime(); // 2012-12-01 14:30:50
$date->getShortDate(); // Dec 1, 2012
$date->getLongDate(); // December 1st, 2012 at 2:30pm
$date->getTime(); // 14:30:50

// You can still define your own formats.
$date->format('jS F, Y'); // 31st January, 2012

You can set a default date format on each instance of Expressive Date which will then be used when you cast the object to a string.

$date = new ExpressiveDate('December 1, 2012 2:30:50 PM');

echo $date; // 1st December, 2012 at 2:30pm

$date->setDefaultDateFormat('d M y');

echo $date; // 1 Dec 12

Expressive Date also comes with a human readable or relative date method.

$date = new ExpressiveDate('December 1, 2012 2:30:50 PM');

$date->getRelativeDate(); // Would show something similar to: 4 days ago

You can also pass in an instance of Expressive Date to compare against, and it's date can also be in the future.

$now = new ExpressiveDate('December 1, 2012 2:30:50 PM');
$future = new ExpressiveDate('December 9, 2012 7:45:32 AM');

$now->getRelativeDate($future); // 1 week from now

Working with Timezones

It's always important to factor in timezones when working with dates and times. Because Expressive Date uses PHPs DateTime class it'll default to using the date defined with date_default_timezone_set().

If you need to you can manipulate the timezone on the fly.

$date = new ExpressiveDate;

$date->setTimezone('Australia/Darwin');

// Or use an instance of DateTimeZone.
$timezone = new DateTimeZone('Australia/Darwin');

$date->setTimezone($timezone);

You can also get an instance of PHPs DateTimeZone if you need it for other manipulations.

$date = new ExpressiveDate;

$timezone = $date->getTimezone();

Or you can just get the name of the timezone.

$date = new ExpressiveDate;

$timezone = $date->getTimezoneName(); // Australia/Melbourne

Changelog

1.0.2

  • Added copy method.
  • Added docblock for magic method hints.
  • Added startOfWeek, endOfWeek, setWeekStartDay, and getWeekStartDay methods.
  • Allowed setWeekStartDay to accept the name of the day as a parameter, e.g., Monday.
  • Fixed exceptions being thrown when using floats for manipulation, e.g., ExpressiveDate::addDays(0.5).
  • Added makeFromDate, makeFromTime, and makeFromDateTime methods.
  • Fixed bug with the week start day being inclusive resulting in 8 day weeks.
  • Added equalTo, sameAs, greaterThan, lessThan, greaterOrEqualTo, and lessOrEqualTo methods.

1.0.1

  • Added the setDefaultDate method.
  • Added __toString method which uses the default date.
  • Removed the String suffix from date formatting methods.

1.0.0

  • Initial release.

License

Expressive Date is licensed under the 2-clause BSD, see the LICENSE file for more details.

Comments
  • minusHours(.5) throws an exception

    minusHours(.5) throws an exception

    Trying to use minusHours() with anything less than one but greater than 0 throws the following exception.

    Exception: DateInterval::__construct(): Unknown or bad format (PT0.5H)
    

    There should be a check inside of modifyHours() that looks for floats between 0 and 1 and redirects them to modifyMinutes instead, since its perfectly reasonable that somebody might be trying to pass a fraction of an hour.

    bug 
    opened by Blackshawk 2
  • Laravel Localization support

    Laravel Localization support

    I've added Laravel Localization support into Expressive Date. This is a non-breaking feature as there is a check whether this module is used inside a Laravel project or not.

    Because my IDE reformatted some code it looks like a lot has been changed, but it's not ;)

    opened by denvers 1
  • i18n for text

    i18n for text

    I would like to use your php extension. I would like to translate (getRelativeDate() / $units prefix, postfix etc.). Can you solve this problem? For example if the extension use language file.. then I be able to translate. Thanks for your support.

    opened by kirsching 1
  • What is the namespace to use via composer?

    What is the namespace to use via composer?

    I'm trying to use ExpressiveDate via composer although I cannot figure it out. I've tried...

    $date = new \ExpressiveDate\ExpressiveDate();
    $date = new \ExpressiveDate();
    $date = new ExpressiveDate();
    
    opened by andruu 1
  • Additional methods: startOfWeek, endOfWeek, copy

    Additional methods: startOfWeek, endOfWeek, copy

    it would be awesome to have some additional methods:

    • startOfWeek() - get start date of the week
    • endOfWeek() - get end date of the week
    • copy() - clone current date (usage: $date->copy()->startOfWeek())

    Week methods also will require week start day definition:

    • setWeekStartDay(0) - set Sunday is first day of the week (by default)
    • setWeekStartDay(1) - set Monday is first day of the week

    Also would be great to hint magic methods like getDay(),setMonth() and etc

    opened by yurytolochko 0
  • Human readable format

    Human readable format

    ~~It'd be great if you could also integrate something like https://pear.php.net/package/Date_HumanDiff to generate time/dates in a human readable format.~~

    Pardon, $date->getRelativeDate(); does that :)

    opened by mrcasual 0
  • Allow public use of modifyDays,Weeks, .. and allow negative amount

    Allow public use of modifyDays,Weeks, .. and allow negative amount

    This way, people can also use modifyDays/Weeks/... directly in their code and can use negative amounts too, otherwise you would need to check for the value in your code and do e.g. addDays,minusDays accordingly.

    opened by liedekef 0
  • README.md example output dates not matching the default format

    README.md example output dates not matching the default format

    The default format is: protected $defaultDateFormat = 'jS F, Y \a\\t g:ia';

    https://github.com/jasonlewis/expressive-date/blob/master/src/ExpressiveDate.php#L36

    But the README.md says the time looks like: $date->startOfWeek(); // 26th November, 2012 at 12:00 AM

    Shouldn't it be?: $date->startOfWeek(); // 26th November, 2012 at 12:00am

    This tripped me up a bit when I was TDDin of my classes.

    opened by clouddueling 0
  • Support for business days and holidays

    Support for business days and holidays

    Have you thought at all about adding support for business days?

    So for example, if

    $date = new ExpressiveDate;  // Let's say this is a Friday
    $date->addDays(1);  // This would give you Saturday
    
    $date->addBusinessDays(1);  // This would give you Monday
    

    Support for holidays would be a little more complicated, because we would probably need to pass in the holidays into object configuration somehow, since it will vary by country / locale.

    But maybe, $holidays were an array of date objects:

    $holidays = array(
        $monday
    );
    ExpressiveDave::initializeHolidays($holidays);
    $date->addBusinessDays(1); // This would be Tuesday, since Monday is holiday
    
    opened by kalenjordan 0
  • Translations for long date

    Translations for long date

    Hi, Major problem with PHP is that we can get long date only in English. I want to be able to get long date also in other languages. For example, in English: 1 Jan 1970 / 1 January 1970 And in Polish: 1 sty 1970 / 1 stycznia 1970 Of course, I don't expect you to include translations by default. I only want to be able to translate it by myself using your lib.

    opened by Cysioland 1
  • Add if less than X days display relative, otherwise use Y

    Add if less than X days display relative, otherwise use Y

    It would be cool to be able to use relative date to a specific length, then use a more normal date.

    Currently I write it something like this (pseudocode):

    $date = new ExpressiveDate('January 31, 1991');
    $current = new ExpressiveDate();
    
    if($current->lessOrEqualTo($date->clone()->addOneWeek())) {
    return $date->getRelativeDate();
    } else {
    return $date->getShortDate();
    }
    
    opened by andrew13 0
Releases(v1.0.2)
Owner
Jason Lewis
Jason Lewis
A standalone DateTime library originally based off of Carbon

CakePHP Chronos Chronos aims to be a drop-in replacement for nesbot/carbon. It focuses on providing immutable date/datetime objects. Immutable objects

CakePHP 1.3k Jan 1, 2023
This library helps PHP users to convert and using Jalali DateTime format

Easy Jalali for PHP V1.0.0 Jalali calendar converter for Persian users in Iran, Afghanistan and other countries that use Jalali calendar. Very thanks

Majid J 3 Mar 20, 2022
Date Manager PHP Class

Date Manager PHP Class Date Manager Version 1.0.0 PHP class for date management, for example converting solar date to gregorian date and vice versa. C

Alireza Tolouei 2 Dec 21, 2021
A simple, standalone, modern PHP class inspector and mapper library, wrapping PHPs native reflection in a fluent interface

A simple, standalone, modern PHP class inspector and mapper library, wrapping PHPs native reflection in a fluent interface.

smpl 9 Sep 1, 2022
A simple PHP API extension for DateTime.

Carbon An international PHP extension for DateTime. http://carbon.nesbot.com <?php use Carbon\Carbon; printf("Right now is %s", Carbon::now()->toDat

Brian Nesbitt 16k Dec 30, 2022
A standalone DateTime library originally based off of Carbon

CakePHP Chronos Chronos aims to be a drop-in replacement for nesbot/carbon. It focuses on providing immutable date/datetime objects. Immutable objects

CakePHP 1.3k Jan 1, 2023
This library helps PHP users to convert and using Jalali DateTime format

Easy Jalali for PHP V1.0.0 Jalali calendar converter for Persian users in Iran, Afghanistan and other countries that use Jalali calendar. Very thanks

Majid J 3 Mar 20, 2022
Makes working with DateTime fields in Laravel's Nova easier

This package adds a DateTime field with support for a global DateTime format, syntactic sugar for formatting individual DateTime fields and powerful d

wdelfuego 6 Aug 4, 2022
The Popular Datetime, Flatpickr Picker as a Filament Form Field

Flatpickr Date/Time Picker as a Filament Field Flatpickr is one of the most popular js datepickers. This filament plugin allows you to use flatpickr a

Savannabits 4 Aug 29, 2022
A Formatter Class for Laravel 4 based on FuelPHP's Formatter Class

Changelog Update support for Laravel 6 & phpunit 8 Update composer.json Upgrade to PSR-4 add parameter newline, delimiter, enclosure, and escape to ex

Soapbox Innovations Inc. 249 Nov 29, 2022
Exploiting and fixing security vulnerabilities of an old version of E-Class. Project implemented as part of the class YS13 Cyber-Security.

Open eClass 2.3 Development of XSS, CSRF, SQLi, RFI attacks/defences of an older,vulnerable version of eclass. Project implemented as part of the clas

Aristi_Papastavrou 11 Apr 23, 2022
PHP Router class - A simple Rails inspired PHP router class.

PHP Router class A simple Rails inspired PHP router class. Usage of different HTTP Methods REST / Resourceful routing Reversed routing using named rou

Danny van Kooten 565 Jan 8, 2023
Caching extension for the Intervention Image Class

Intervention Image Cache Intervention Image Cache extends the Intervention Image Class package to be capable of image caching functionality. The libra

null 616 Dec 30, 2022
Is an Extension of Laravel View Class which compiles String Template on the fly. It automatically detects changes on your string template and recompiles it if needed.

Laravel-fly-view Is an Extension of Laravel View Class which compiles String Template on the fly. It automatically detects changes on your string temp

John Turingan 16 Jul 17, 2022
Extension for the Laravel validation class

Intervention Validation Intervention Validation is an extension library for Laravel's own validation system. The package adds rules to validate data l

null 370 Dec 30, 2022
Phpstan-dba - database handling related class reflection extension for PHPStan & framework-specific rules

database handling class reflection extension for PHPStan This extension provides following features: PDO->query knows the array shape of the returned

Markus Staab 175 Dec 29, 2022
Caching extension for the Intervention Image Class

Intervention Image Cache extends the Intervention Image Class package to be capable of image caching functionality.

null 616 Dec 30, 2022
A TYPO3 extension that integrates the Apache Solr search server with TYPO3 CMS. dkd Internet Service GmbH is developing the extension. Community contributions are welcome. See CONTRIBUTING.md for details.

Apache Solr for TYPO3 CMS A TYPO3 extension that integrates the Apache Solr enterprise search server with TYPO3 CMS. The extension has initially been

Apache Solr for TYPO3 126 Dec 7, 2022
This extension expands WSOAuth extension and provide a EveOnline SSO login method

This extension expands WSOAuth extension and provide a EveOnline SSO login method

Raze Soldier 1 Nov 15, 2021
Magento 2 Extension to cleanup admin menu and Store > Configuration area by arranging third party extension items.

Clean Admin Menu - Magento 2 Extension It will merge all 3rd party extension's menu items in backend's primary menu to a common menu item named "Exten

RedChamps 109 Jan 3, 2023