1 /*
2 * The basecode project
3 *
4 * Copyright (c) 2006 University of British Columbia
5 *
6 * Licensed under the Apache License, Version 2.0 (the "License");
7 * you may not use this file except in compliance with the License.
8 * You may obtain a copy of the License at
9 *
10 * http://www.apache.org/licenses/LICENSE-2.0
11 *
12 * Unless required by applicable law or agreed to in writing, software
13 * distributed under the License is distributed on an "AS IS" BASIS,
14 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15 * See the License for the specific language governing permissions and
16 * limitations under the License.
17 *
18 */
19 package ubic.basecode.util;
20
21 import java.text.ParseException;
22 import java.text.SimpleDateFormat;
23 import java.util.Calendar;
24 import java.util.Collection;
25 import java.util.Date;
26 import java.util.regex.Matcher;
27 import java.util.regex.Pattern;
28
29 import org.apache.commons.lang3.time.DateUtils;
30
31 /**
32 * Date Utility Class
33 *
34 * @author pavlidis
35 * @author <a href="mailto:matt@raibledesigns.com">Matt Raible</a> Modified by <a href="mailto:dan@getrolling.com">Dan
36 * Kibler </a> to correct time pattern. Minutes should be mm not MM (MM is month).
37 * @version $Revision$ $Date$
38 */
39 public class DateUtil {
40 // ~ Static fields/initializers =============================================
41
42 private static String datePattern = "MM/dd/yyyy";
43
44 // ~ Methods ================================================================
45
46 /**
47 * This method generates a string representation of a date based on the System Property 'dateFormat' in the format
48 * you specify on input
49 *
50 * @param aDate A date to convert
51 * @return a string representation of the date
52 */
53 public static final String convertDateToString( Date aDate ) {
54 return getDateTime( datePattern, aDate );
55 }
56
57 /**
58 * This method generates a string representation of a date/time in the format you specify on input
59 *
60 * @param aMask the date pattern the string is in
61 * @param strDate a string representation of a date
62 * @return a converted Date object
63 * @see java.text.SimpleDateFormat
64 * @throws ParseException
65 */
66 public static final Date convertStringToDate( String aMask, String strDate ) throws ParseException {
67 SimpleDateFormat df = null;
68 Date date = null;
69 df = new SimpleDateFormat( aMask );
70
71 try {
72 date = df.parse( strDate );
73 } catch ( ParseException pe ) {
74 throw new ParseException( pe.getMessage(), pe.getErrorOffset() );
75 }
76
77 return ( date );
78 }
79
80 /**
81 * This method generates a string representation of a date's date/time in the format you specify on input
82 *
83 * @param aMask the date pattern the string is in
84 * @param aDate a date object
85 * @return a formatted string representation of the date
86 * @see java.text.SimpleDateFormat
87 */
88 public static final String getDateTime( String aMask, Date aDate ) {
89 SimpleDateFormat df = null;
90 String returnValue = "";
91
92 if ( aDate != null ) {
93 df = new SimpleDateFormat( aMask );
94 returnValue = df.format( aDate );
95 }
96
97 return returnValue;
98 }
99
100 /**
101 * Turn a string like '-7d' into the date equivalent to "seven days ago". Supports 'd' for day, 'h' for hour, 'm'
102 * for minutes, "M" for months and "y" for years. Start with a '-' to indicate times in the past ('+' is not
103 * necessary for future). Values must be integers.
104 *
105 * @param date to be added/subtracted to
106 * @param dateString
107 * @author Paul Pavlidis
108 * @return Date relative to 'now' as modified by the input date string.
109 */
110 public static Date getRelativeDate( Date date, String dateString ) {
111
112 if ( date == null ) throw new IllegalArgumentException( "Null date" );
113
114 Pattern pat = Pattern.compile( "([+-]?[0-9]+)([dmhMy])" );
115
116 Matcher match = pat.matcher( dateString );
117 boolean matches = match.matches();
118
119 if ( !matches ) {
120 throw new IllegalArgumentException( "Couldn't make sense of " + dateString
121 + ", please use something like -7d or -8h" );
122 }
123
124 int amount = Integer.parseInt( match.group( 1 ).replace( "+", "" ) );
125 String unit = match.group( 2 );
126
127 if ( unit.equals( "h" ) ) {
128 return DateUtils.addHours( date, amount );
129 } else if ( unit.equals( "m" ) ) {
130 return DateUtils.addMinutes( date, amount );
131 } else if ( unit.equals( "d" ) ) {
132 return DateUtils.addDays( date, amount );
133 } else if ( unit.equals( "y" ) ) {
134 return DateUtils.addYears( date, amount );
135 } else if ( unit.equals( "M" ) ) {
136 return DateUtils.addMonths( date, amount );
137 } else {
138 throw new IllegalArgumentException( "Couldn't make sense of units in " + dateString
139 + ", please use something like -7d or -8h" );
140 }
141
142 }
143
144 /**
145 * return today date as a String
146 *
147 * @param boolean changes character '\' to '-', (used to write files)
148 * @return String today date
149 */
150 public static String getTodayDate( boolean changeDateformat ) {
151
152 String todayDate = convertDateToString( Calendar.getInstance().getTime() );
153
154 // changes character '\' to '-', (used to write files)
155 if ( changeDateformat ) {
156 todayDate = todayDate.replaceAll( "/", "-" );
157 }
158 return todayDate;
159 }
160
161 /**
162 * Compute the number of seconds spanned by the given dates. If no or a single date is provided, returns 0.
163 *
164 * @param dates
165 * @return
166 */
167 public static long numberOfSecondsBetweenDates( Collection<Date> dates ) {
168 if ( dates == null ) throw new IllegalArgumentException();
169 if ( dates.size() < 2 ) return 0;
170 // dates we are sure are safe...
171 Date max = DateUtils.addYears( new Date(), -500 );
172 Date min = DateUtils.addYears( new Date(), 500 );
173 for ( Date d : dates ) {
174 if ( d.before( min ) ) {
175 min = d;
176 }
177
178 if ( d.after( max ) ) {
179 max = d;
180 }
181 }
182 return Math.round( ( max.getTime() - min.getTime() ) / 1000.00 );
183 }
184 }