mirror of
https://github.com/openharmony/miscservices_time.git
synced 2026-07-20 23:44:54 -04:00
9a9bae6f26
Signed-off-by: guduhanyan <xuyanjun27@163.com>
176 lines
5.4 KiB
C++
176 lines
5.4 KiB
C++
/*
|
|
* Copyright (C) 2021 Huawei Device Co., Ltd.
|
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
* you may not use this file except in compliance with the License.
|
|
* You may obtain a copy of the License at
|
|
*
|
|
* http://www.apache.org/licenses/LICENSE-2.0
|
|
*
|
|
* Unless required by applicable law or agreed to in writing, software
|
|
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
* See the License for the specific language governing permissions and
|
|
* limitations under the License.
|
|
*/
|
|
|
|
#include "time_zone_info.h"
|
|
|
|
|
|
namespace OHOS{
|
|
namespace MiscServices{
|
|
namespace {
|
|
static const int HOURS_TO_MINUTES = 60;
|
|
}
|
|
|
|
TimeZoneInfo::TimeZoneInfo()
|
|
{
|
|
std::vector<struct zoneInfoEntry> timezoneList = {
|
|
{"Antarctica/McMurdo", "AQ", 12},
|
|
{"America/Argentina/Buenos_Aires", "AR", -3},
|
|
{"Australia/Sydney", "AU", 10},
|
|
{"America/Noronha", "BR", -2},
|
|
{"America/St_Johns", "CA", -2.5},
|
|
{"Africa/Kinshasa", "CD", 1},
|
|
{"America/Santiago", "CL", -3},
|
|
{"Asia/Shanghai", "CN", 8},
|
|
{"Asia/Nicosia", "CY", 3},
|
|
{"Europe/Berlin", "DE", 2},
|
|
{"America/Guayaquil", "CEST", -5},
|
|
{"Europe/Madrid", "ES", 2},
|
|
{"Pacific/Pohnpei", "FM", 11},
|
|
{"America/Godthab", "GL", -2},
|
|
{"Asia/Jakarta", "ID", 7},
|
|
{"Pacific/Tarawa", "KI", 12},
|
|
{"Asia/Almaty", "KZ", 6},
|
|
{"Pacific/Majuro", "MH", 12},
|
|
{"Asia/Ulaanbaatar", "MN", 8},
|
|
{"America/Mexico_City", "MX", -5},
|
|
{"Asia/Kuala_Lumpur", "MY", 8},
|
|
{"Pacific/Auckland", "NZ", 12},
|
|
{"Pacific/Tahiti", "PF", -10},
|
|
{"Pacific/Port_Moresby", "PG", 10},
|
|
{"Asia/Gaza", "PS", 3},
|
|
{"Europe/Lisbon", "PT", 1},
|
|
{"Europe/Moscow", "RU", 3},
|
|
{"Europe/Kiev", "UA", 3},
|
|
{"Pacific/Wake", "UM", 12},
|
|
{"America/New_York", "US", -4},
|
|
{"Asia/Tashkent", "UZ", 5}
|
|
};
|
|
|
|
for (auto tz : timezoneList) {
|
|
timezoneInfoMap_[tz.ID] = tz;
|
|
}
|
|
}
|
|
|
|
TimeZoneInfo::~TimeZoneInfo()
|
|
{
|
|
timezoneInfoMap_.clear();
|
|
}
|
|
|
|
void TimeZoneInfo::Init()
|
|
{
|
|
TIME_HILOGD(TIME_MODULE_SERVICE, "start.");
|
|
std::string timezoneId;
|
|
float gmtOffset;
|
|
if (!GetTimezoneFromFile(timezoneId)) {
|
|
TIME_HILOGE(TIME_MODULE_SERVICE, "end, init timezone failed.");
|
|
return;
|
|
}
|
|
if (!GetOffsetById(timezoneId, gmtOffset)) {
|
|
TIME_HILOGE(TIME_MODULE_SERVICE, "end, init timezone failed.");
|
|
return;
|
|
}
|
|
if (!SetOffsetToKernel(gmtOffset)) {
|
|
TIME_HILOGE(TIME_MODULE_SERVICE, "end, init timezone failed.");
|
|
return;
|
|
}
|
|
TIME_HILOGD(TIME_MODULE_SERVICE, "end.");
|
|
}
|
|
|
|
bool TimeZoneInfo::SetTimezone(std::string timezoneId)
|
|
{
|
|
float gmtOffset;
|
|
if (!GetOffsetById(timezoneId, gmtOffset)) {
|
|
TIME_HILOGE(TIME_MODULE_SERVICE, "Timezone unsupport %{public}s.", timezoneId.c_str());
|
|
return false;
|
|
}
|
|
TIME_HILOGD(TIME_MODULE_SERVICE, "timezone :%{public}s , GMT Offset :%{public}f", timezoneId.c_str(), gmtOffset);
|
|
if (!SetOffsetToKernel(gmtOffset)) {
|
|
TIME_HILOGE(TIME_MODULE_SERVICE, "Set kernel failed.");
|
|
return false;
|
|
}
|
|
if (!SaveTimezoneToFile(timezoneId)) {
|
|
TIME_HILOGE(TIME_MODULE_SERVICE, "Save file failed.");
|
|
return false;
|
|
}
|
|
curTimezoneId_ = timezoneId;
|
|
return true;
|
|
}
|
|
|
|
bool TimeZoneInfo::GetTimezone(std::string &timezoneId) {
|
|
timezoneId = curTimezoneId_;
|
|
return true;
|
|
}
|
|
|
|
bool TimeZoneInfo::SetOffsetToKernel(float offsetHour)
|
|
{
|
|
struct timezone tz{};
|
|
tz.tz_minuteswest = static_cast<int>(offsetHour * HOURS_TO_MINUTES);
|
|
tz.tz_dsttime = 0;
|
|
TIME_HILOGD(TIME_MODULE_SERVICE, "settimeofday, Offset hours :%{public}f , Offset minutes :%{public}d", offsetHour, tz.tz_minuteswest);
|
|
int result = settimeofday(NULL, &tz);
|
|
if (result < 0) {
|
|
TIME_HILOGE(TIME_MODULE_SERVICE, "settimeofday fail: %{public}d.",result);
|
|
return false;
|
|
}
|
|
return true;
|
|
}
|
|
|
|
bool TimeZoneInfo::GetTimezoneFromFile(std::string &timezoneId)
|
|
{
|
|
Json::Value root;
|
|
std::ifstream ifs;
|
|
ifs.open(TIMEZONE_FILE_PATH);
|
|
Json::CharReaderBuilder builder;
|
|
builder["collectComments"] = true;
|
|
JSONCPP_STRING errs;
|
|
if (!parseFromStream(builder, ifs, &root, &errs)) {
|
|
ifs.close();
|
|
TIME_HILOGE(TIME_MODULE_SERVICE, "Read file failed %{public}s.", errs.c_str());
|
|
return false;
|
|
}
|
|
timezoneId = root["TimezoneId"].asString();
|
|
TIME_HILOGE(TIME_MODULE_SERVICE, "Read file %{public}s.", timezoneId.c_str());
|
|
ifs.close();
|
|
return true;
|
|
}
|
|
|
|
bool TimeZoneInfo::SaveTimezoneToFile(std::string timezoneId)
|
|
{
|
|
std::ofstream ofs;
|
|
ofs.open(TIMEZONE_FILE_PATH);
|
|
Json::Value root;
|
|
root["TimezoneId"] = timezoneId;
|
|
Json::StreamWriterBuilder builder;
|
|
const std::string json_file = Json::writeString(builder, root);
|
|
ofs << json_file;
|
|
ofs.close();
|
|
TIME_HILOGD(TIME_MODULE_SERVICE, "Write file %{public}s.", timezoneId.c_str());
|
|
return true;
|
|
}
|
|
|
|
bool TimeZoneInfo::GetOffsetById(const std::string timezoneId, float &offset)
|
|
{
|
|
auto itEntry = timezoneInfoMap_.find(timezoneId);
|
|
if (itEntry != timezoneInfoMap_.end()) {
|
|
auto zoneInfo = itEntry->second;
|
|
offset = zoneInfo.utcOffsetHours;
|
|
curTimezoneId_ = timezoneId;
|
|
return true;
|
|
}
|
|
TIME_HILOGE(TIME_MODULE_SERVICE, "TimezoneId not found.");
|
|
return false;
|
|
}
|
|
}
|
|
} |