Yii global date format (l18n) - date

When I type:
Yii::app()->getLocale()->dateFormat
it gives me the correct dateformat for the current set language. (in my example it is 'de' => dd.MM.yyyy). But when I type:
Yii::app()->format->dateFormat
Yii gives me the date format for 'en_us' (Y/m/d).
With getLocale() I will get only the string saved in i18n file. In ->format->date() this format string should be used, but I don't find a way to assign the i18n string to the CDateFormatter or CFormatter Object.

The CFormatter component accessed with Yii::app()->format is not meant to be used for localization out of the box; it does not automatically work according to the application locale.
You could manually change the relevant properties on Yii::app()->format to bring it in line with the application locale, but there is a more convenient way to format dates:
Yii::app()->locale->dateFormatter->formatDateTime(...)
See CDateFormatter::formatDateTime for more information; if you want more control, there are other methods such as CDateFormatter::format available. Also keep in mind that CLocale::getNumberFormatter() is available to format numbers.

Related

Date type required in AEM HTL / Sightly date formatter

I've seen that since AEM 6.3, date formatting has been natively supported in the markup, like so:
${ 'dd~MMMM-yyyy' # format=currentPage.jcr:created }
(Reference: https://github.com/adobe/htl-spec/blob/master/SPECIFICATION.md#1222-dates )
I have tried playing with this formatter using that jcr:created property, as well as data coming from the backend in java.util.Date.
My question is, are other date types supported? Like say, java.time.LocalDate? It doesn't display on my test pages, although I'm not sure if I'm just missing some additional property that needs to be indicated on the HTL markup?
It's not mentioned in the documentation as far as I can tell but Apache Sling is an open source project so we can look it up on our own.
Looking at the implementation details, the only supported types as of now are java.util.Date and java.util.Calendar and their sub-classes.
Here's the FormatFilterExtension class responsible for applying the chosen format in HTL.
Let's have a look at the check it performs.
} else if (DATE_FORMAT_TYPE.equals(formattingType) || (!hasPlaceHolders && runtimeObjectModel.isDate(formatObject))) {
Locale locale = getLocale(runtimeObjectModel, options);
TimeZone timezone = getTimezone(runtimeObjectModel, options);
return formatDate(source, runtimeObjectModel.toDate(formatObject), locale, timezone);
}
It uses runtimeObjectModel.isDate() to verify if we're dealing with a date. If we look at runtimeObjectModel, we can see that it's an instance of SlingRuntimeObjectModel which in turn extends AbstractRuntimeModel.
#Override
public boolean isDate(Object target) {
return (target instanceof Date || target instanceof Calendar);
}
so if it's a Date or a Calendar, it will be handled.
Even if you force the formatting type like this
${'yyyy-MM-dd' # format=myDate, type='date'} <!--/* Forced formatting type */-->
the object you pass will end up being processed using AbstractRuntimeObjectModel#toDate(Object object) which returns null for all objects that aren't instances of Date or Calendar.
Since the check is based on instanceof, this also includes instances of Date and Calendar's sub-types. LocalDate, however, is not one of them so it's not surprising that it didn't work.

Changing the default date format in classic asp when using the "date" function

I'm migrating a whole bunch of web pages that were written in classic asp over to a new server, and have discovered many references to the simple date() function, like:
if cint(left(date,instr(date,"/")-1)) < 9 then blah blah
I'm getting errors because the new server's default date format is returning yyyy-mm-dd, and the code above is expecting it to be in dd/mm/yyyy format.
Rather than manually fixing every occurrence, of which there could be hundreds, I'm looking to see if I can change the default date format for asp so that date() returns dd/mm/yyyy. I thought by simply changing the system's short date format would do the trick, but even after restarting the server it's still showing yyyy-mm-dd.
Is there a setting somewhere where you can specify the default date format when using the date() function?
This worked for me:
change global.asa, in the Sub Session_OnStart, add a line
Session.LCID=1033

How to handle date input in Laravel

I'm working on an app that allows the user to edit several dates in a form. The dates are rendered in the European format (DD-MM-YYYY) while the databases uses the default YYYY-MM-DD format.
There are several ways to encode/decode this data back and forth from the database to the user, but they all require a lot of code:
Use a helper function to convert the date before saving and after retrieving (very cumbersome, requires much code)
Create a separate attribute for each date attribute, and use the setNameAttribute and getNameAttribute methods to decode/encode (also cumbersome and ugly, requires extra translations/rules for each attribute)
Use JavaScript to convert the dates when loading and submitting the form (not very reliable)
So what's the most efficient way to store, retrieve and validate dates and times from the user?
At some point, you have to convert the date from the view format to the database format. As you mentioned, there are a number of places to do this, basically choosing between the back-end or the front-end.
I do the conversion at the client side (front-end) using javascript (you can use http://momentjs.com to help with this). The reason is that you may need different formats depending on the locale the client is using (set in the browser or in his profile preferences for example). Doing the format conversion in the front-end allows you to convert to these different date formats easily.
Another advantage is that you can then use the protected $dates property in your model to have Laravel handle (get and set) these dates automatically as a Carbon object, without the need for you to do this (see https://github.com/laravel/framework/blob/master/src/Illuminate/Database/Eloquent/Model.php#L126).
As for validation, you need can then use Laravel's built-in validation rules for dates, like this:
'date' => 'required|date|date_format:Y-n-j'
While client-side is good for UX, it doesn't let you be sure, all will be good.
At some point you will need server-side validation/convertion anyway.
But here's the thing, it's as easy as this:
// after making sure it's valid date in your format
// $dateInput = '21-02-2014'
$dateLocale = DateTime::createFromFormat('d-m-Y', $dateInput);
// or providing users timezone
$dateLocale =
DateTime::createFromFormat('d-m-Y', $dateInput, new DateTime('Europe/London'));
$dateToSave = $dateLocale
// ->setTimeZone(new TimeZone('UTC')) if necessary
->format('Y-m-d');
et voila!
Obviously, you can use brilliant Carbon to make it even easier:
$dateToSave = Carbon::createFromFormat('d-m-Y', $dateInput, 'Europe/London')
->tz('UTC')
->toDateString(); // '2014-02-21'
Validation
You say that Carbon throws exception if provided with wrong input. Of course, but here's what you need to validate the date:
'regex:/\d{1,2}-\d{1,2}-\d{4}/|date_format:d-m-Y'
// accepts 1-2-2014, 01-02-2014
// doesn't accept 01-02-14
This regex part is necessary, if you wish to make sure year part is 4digit, since PHP would consider date 01-02-14 valid, despite using Y format character (making year = 0014).
The best way I found is overriding the fromDateTime from Eloquent.
class ExtendedEloquent extends Eloquent {
public function fromDateTime($value)
{
// If the value is in simple day, month, year format, we will format it using that setup.
// To keep using Eloquent's original fromDateTime method, we'll convert the date to timestamp,
// because Eloquent already handle timestamp.
if (preg_match('/^(\d{2})\/(\d{2})\/(\d{4})$/', $value)) {
$value = Carbon\Carbon::createFromFormat('d/m/Y', $value)
->startOfDay()
->getTimestamp();
}
return parent::fromDateTime($value);
}
}
I'm new in PHP, so I don't know if it's the best approach.
Hope it helps.
Edit:
Of course, remember to set all your dates properties in dates inside your model. eg:
protected $dates = array('IssueDate', 'SomeDate');

Customizing phone number or any other String for different Locales in GWT

I am trying to find the best route to get in some Custom formats I need. For example if I have a phone number 0803456765
In India it may be represented as +91 (080) 3456765
In US it may be 080-345-6765 and so on
I could keep the format in the properties file and based on locale I could pull the format and format the String. I could also have a Util class which does this for me after I identify the Locale.
But I think there might be a better route using NumberFormat. I guess NumberFormat automatically figures out the Locale and applies a certain Pattern to the String. Can I customize this pattern ? In the sense, can I tell GWT to use my Custom pattern for the US Locale
I know we can do this
// Custom format
value = 12345.6789;
formatted = NumberFormat.getFormat("000000.000000").format(value);
// prints 012345.678900 in the default locale
GWT.log("Formatted string is" + formatted, null);
but I don't want to specify my formatting pattern as in 'NumberFormat.getFormat("000000.000000")'. I want to override the default number formats of various Locales in GWT to achieve this. How do I do this ?
Don't roll your own. Google open sourced their library which you can leverage. It supports
Parsing/formatting/validating phone numbers for all countries/regions
of the world.

Why do I need to parse dates in Grails?

I am in the unfortunate position that I need to use a composite id in a Grails app where I work with legacy data. This means I have to override some actions in the controller, but as I did this I was struck by the fact that I could not use use a date argument directly as a parameter to a dynamic method.
Instead of just doing MyLegacyObj.findBySystemIdAndLogDate(params.systemId, params.logDate), I first needed to parse the date string before giving it to the dynamic method. To further complicate matters I had no idea what format the date string had (until I added lots of log.debug() string to the output). So now I have a bit of code looking like this
def formatter = new SimpleDateFormat("EEE MMM d HH:mm:ss z yyyy")
MyLegacyObj.findBySystemIdAndLogDate(params.systemId, formatter.parse(params.logDate));
This feels unoptimal, no to say dangerous (what if the date format changes with the locale?)? What would be a recommended way of doing this, and do I really need to parse dates at all?
Date is a pretty complex object and params are just Strings, so Date is submitted in parts. It is "magically" assembled from the parts when assigning x.properties = params.
Command object will do the work for you, if you add a Date field to it.
It has nothing to do with methods' dynamic or static invocation. Your GSP that renders Date editor might interfere too.