Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(31)

Side by Side Diff: net/ftp/ftp_util.cc

Issue 6697021: FTP: use ICU to parse month abbreviations. (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src
Patch Set: copyright years Created 9 years, 9 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
« no previous file with comments | « net/ftp/ftp_util.h ('k') | no next file » | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright (c) 2009 The Chromium Authors. All rights reserved. 1 // Copyright (c) 2011 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #include "net/ftp/ftp_util.h" 5 #include "net/ftp/ftp_util.h"
6 6
7 #include <vector> 7 #include <vector>
8 8
9 #include "base/logging.h" 9 #include "base/logging.h"
10 #include "base/string_number_conversions.h" 10 #include "base/string_number_conversions.h"
11 #include "base/string_tokenizer.h" 11 #include "base/string_tokenizer.h"
12 #include "base/string_util.h" 12 #include "base/string_util.h"
13 #include "base/time.h" 13 #include "base/time.h"
14 #include "base/utf_string_conversions.h" 14 #include "base/utf_string_conversions.h"
15 #include "unicode/datefmt.h"
16 #include "unicode/dtfmtsym.h"
15 17
16 // For examples of Unix<->VMS path conversions, see the unit test file. On VMS 18 // For examples of Unix<->VMS path conversions, see the unit test file. On VMS
17 // a path looks differently depending on whether it's a file or directory. 19 // a path looks differently depending on whether it's a file or directory.
18 20
19 namespace net { 21 namespace net {
20 22
21 // static 23 // static
22 std::string FtpUtil::UnixFilePathToVMS(const std::string& unix_path) { 24 std::string FtpUtil::UnixFilePathToVMS(const std::string& unix_path) {
23 if (unix_path.empty()) 25 if (unix_path.empty())
24 return std::string(); 26 return std::string();
(...skipping 76 matching lines...) Expand 10 before | Expand all | Expand 10 after
101 std::replace(result.begin(), result.end(), ']', '/'); 103 std::replace(result.begin(), result.end(), ']', '/');
102 104
103 // Make sure the result doesn't end with a slash. 105 // Make sure the result doesn't end with a slash.
104 if (result.length() && result[result.length() - 1] == '/') 106 if (result.length() && result[result.length() - 1] == '/')
105 result = result.substr(0, result.length() - 1); 107 result = result.substr(0, result.length() - 1);
106 108
107 return result; 109 return result;
108 } 110 }
109 111
110 // static 112 // static
111 bool FtpUtil::ThreeLetterMonthToNumber(const string16& text, int* number) { 113 bool FtpUtil::AbbreviatedMonthToNumber(const string16& text, int* number) {
112 const static char* months[] = { "jan", "feb", "mar", "apr", "may", "jun", 114 icu::UnicodeString unicode_text(text.data(), text.size());
113 "jul", "aug", "sep", "oct", "nov", "dec" };
114 115
115 for (size_t i = 0; i < arraysize(months); i++) { 116 int32_t locales_count;
116 if (LowerCaseEqualsASCII(text, months[i])) { 117 const icu::Locale* locales =
117 *number = i + 1; 118 icu::DateFormat::getAvailableLocales(locales_count);
118 return true; 119
120 // Some FTP servers localize the date listings. To guess the locale,
121 // we loop over all available ones.
122 for (int32_t locale = 0; locale < locales_count; locale++) {
123 UErrorCode status(U_ZERO_ERROR);
124
125 icu::DateFormatSymbols format_symbols(locales[locale], status);
126
127 // If we cannot get format symbols for some locale, it's not a fatal error.
128 // Just try another one.
129 if (U_FAILURE(status))
130 continue;
131
132 int32_t months_count;
133 const icu::UnicodeString* months =
134 format_symbols.getShortMonths(months_count);
135
136 // Loop over all abbreviated month names in given locale.
137 // An alternative solution (to parse |text| in given locale) is more
138 // lenient, and may accept more than we want even with setLenient(false).
139 for (int32_t month = 0; month < months_count; month++) {
140 if (months[month].caseCompare(unicode_text, 0) == 0) {
141 *number = month + 1;
142 return true;
143 }
119 } 144 }
120 } 145 }
121 146
122 // Special cases for directory listings in German (other three-letter month
123 // abbreviations are the same as in English). Note that we don't need to do
124 // a case-insensitive compare here. Only "ls -l" style listings may use
125 // localized month names, and they will always start capitalized. Also,
126 // converting non-ASCII characters to lowercase would be more complicated.
127 if (text == UTF8ToUTF16("M\xc3\xa4r")) {
128 // The full month name is M-(a-umlaut)-rz (March), which is M-(a-umlaut)r
129 // when abbreviated.
130 *number = 3;
131 return true;
132 }
133 if (text == ASCIIToUTF16("Mai")) {
134 *number = 5;
135 return true;
136 }
137 if (text == ASCIIToUTF16("Okt")) {
138 *number = 10;
139 return true;
140 }
141 if (text == ASCIIToUTF16("Dez")) {
142 *number = 12;
143 return true;
144 }
145
146 return false; 147 return false;
147 } 148 }
148 149
149 // static 150 // static
150 bool FtpUtil::LsDateListingToTime(const string16& month, const string16& day, 151 bool FtpUtil::LsDateListingToTime(const string16& month, const string16& day,
151 const string16& rest, 152 const string16& rest,
152 const base::Time& current_time, 153 const base::Time& current_time,
153 base::Time* result) { 154 base::Time* result) {
154 base::Time::Exploded time_exploded = { 0 }; 155 base::Time::Exploded time_exploded = { 0 };
155 156
156 if (!ThreeLetterMonthToNumber(month, &time_exploded.month)) 157 if (!AbbreviatedMonthToNumber(month, &time_exploded.month))
157 return false; 158 return false;
158 159
159 if (!base::StringToInt(day, &time_exploded.day_of_month)) 160 if (!base::StringToInt(day, &time_exploded.day_of_month))
160 return false; 161 return false;
161 162
162 if (!base::StringToInt(rest, &time_exploded.year)) { 163 if (!base::StringToInt(rest, &time_exploded.year)) {
163 // Maybe it's time. Does it look like time (HH:MM)? 164 // Maybe it's time. Does it look like time (HH:MM)?
164 if (rest.length() == 5 && rest[2] == ':') { 165 if (rest.length() == 5 && rest[2] == ':') {
165 if (!base::StringToInt(rest.begin(), 166 if (!base::StringToInt(rest.begin(),
166 rest.begin() + 2, 167 rest.begin() + 2,
(...skipping 52 matching lines...) Expand 10 before | Expand all | Expand 10 after
219 while (pos < text.length() && !isspace(text[pos])) 220 while (pos < text.length() && !isspace(text[pos]))
220 pos++; 221 pos++;
221 } 222 }
222 223
223 string16 result(text.substr(pos)); 224 string16 result(text.substr(pos));
224 TrimWhitespace(result, TRIM_ALL, &result); 225 TrimWhitespace(result, TRIM_ALL, &result);
225 return result; 226 return result;
226 } 227 }
227 228
228 } // namespace 229 } // namespace
OLDNEW
« no previous file with comments | « net/ftp/ftp_util.h ('k') | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698