LINUX時區設定及與資料庫之間(ORACLE MYSQL)的關係

luckyfriends發表於2016-12-21

LINUX時區
   LINUX 作業系統時區由/etc/localtime設定,其可以是一個指向/usr/share/zoneinfo下檔案的軟連線,
當然也可以複製,在/usr/share/zoneinfo目錄下每個檔案都包含了特定地區的時區資訊,很多都分為
洲目錄/地區目錄 
如:
UTC:GMT標準時間+0時區
CET:歐洲中部時間
EST:美國東部標準時間
Asia/Shanghai:中國上海+8時區  (亞洲目錄/上海地區)
我們可以簡單的建立一個連線
cd /etc
ln -s  /usr/share/zoneinfo/Asia/Shanghai  /etc/localtime 
[root@testmy etc]# date -R
Wed, 07 Dec 2016 06:30:53 +0800
[root@testmy etc]# unlink localtime
[root@testmy etc]# ln -s  /usr/share/zoneinfo/UTC  /etc/localtime 
[root@testmy etc]# date -R
Tue, 06 Dec 2016 22:31:18 +0000

也可以複製:
[root@testmy etc]# cp /usr/share/zoneinfo/UTC localtime
cp: overwrite `localtime'? y
[root@testmy etc]# date
Wed Dec  7 00:13:22 UTC 2016
[root@testmy etc]# cp /usr/share/zoneinfo/Asia/Shanghai localtime
cp: overwrite `localtime'? y
[root@testmy etc]# date
Wed Dec  7 08:13:41 CST 2016

可以看到時區的變換,注意時區更改變資料庫某些函式的返回

ORACLE資料庫SYSDATE和SYSTIMESTAMP函式的返回將會隨著系統時區的改變而改變,LOCALTIMESTAMP
CURRENT_TIMESTAMP和CURRENT_DATE ,它們跟隨的是會話級別的時區也就是應用連線本地時區
下來是來自metalink的描述:

LOCALTIMESTAMP returns the current date and time in the session time zone in
 a value of datatype TIMESTAMP, that is date time similar to CURRENT_DATE 
 but the datatype is TIMESTAMP.
 
CURRENT_TIMESTAMP returns the current date and time in the session time zone,
 in a value of datatype TIMESTAMP WITH TIME ZONE, that is date time similar to 
 CURRENT_DATE but the datatype is TIMESTAMP WITH TIME ZONE.

SYSTIMESTAMP returns the system date, including fractional seconds and time zone,
 of the system on which the database resides. The return type is TIMESTAMP WITH 
 TIME ZONE. Unlike SYSDATE, which you can set to a constant using FIXED_DATE, 
 SYSTIMESTAMP will give the system date even though FIXED_DATE is set.
 
"SYSDATE" and "SYSTIMESTAMP" are purely dependent on the operating system clock, 
hence it IS depending on the timezone information of this operating system and/or 
the operating system settings when the database and listener where started.


列子:
SQL>  select to_CHAR(systimestamp,'YYYY-MM-DD HH24:MI:SS:TZR') from dual;
TO_CHAR(SYSTIMESTAMP,'YYYY-MM-
----------------------------------------------------
2016-12-06 23:00:16:+00:00


更改系統時區後,重新連線一個session
SQL>  select to_CHAR(systimestamp,'YYYY-MM-DD HH24:MI:SS:TZR') from dual;
TO_CHAR(SYSTIMESTAMP,'YYYY-MM-
----------------------------------------------------
2016-12-07 07:00:58:+08:00

看到時區改變了

MYSQL資料庫如果設定引數:
time_zone 為system,那麼代表每一個連線執行緒使用伺服器OS的系統時間
那麼時區受
| system_time_zone                   | UTC               |
的影響,可以看到我這裡是UTC標準時區
那麼這個時候某些函式如now(),current_time(),sysdate()都將受到影響,
但是和ORACLE不同如果MYSQL資料庫不重啟資料庫將不會受到影響

列子:
mysql> show variables like '%time_zone%';
+------------------+--------+
| Variable_name    | Value  |
+------------------+--------+
| system_time_zone | UTC    |
| time_zone        | SYSTEM |
+------------------+--------+
2 rows in set (0.00 sec)


mysql> select now(),current_time(),sysdate();
+---------------------+----------------+---------------------+
| now()               | current_time() | sysdate()           |
+---------------------+----------------+---------------------+
| 2016-12-06 23:06:17 | 23:06:17       | 2016-12-06 23:06:17 |
+---------------------+----------------+---------------------+
更改OS時區後重啟MYSQL資料庫
mysql> show variables like '%time_zone%';
+------------------+--------+
| Variable_name    | Value  |
+------------------+--------+
| system_time_zone | CST    |
| time_zone        | SYSTEM |
+------------------+--------+
2 rows in set (0.00 sec)

mysql> select now(),current_time(),sysdate();
+---------------------+----------------+---------------------+
| now()               | current_time() | sysdate()           |
+---------------------+----------------+---------------------+
| 2016-12-07 07:07:11 | 07:07:11       | 2016-12-07 07:07:11 |
+---------------------+----------------+---------------------+
1 row in set (0.00 sec)
可以看到時區改變。
當然time_zone是連線級別可以設定的,我們可以設定它為正確的時區,而不依賴
OS的時區如:set global  time_zone = '+8:00'; 


最後還是給出一段簡單的程式碼用於檢視時區的變化對系統時間的影響

gaopeng@bogon:~/linuxapinew$ TZ="Asia/Shanghai"  ./a.out 
ctime() is:Wed Dec 28 19:15:55 2016
asmtime is:Wed Dec 28 19:15:55 2016
gaopeng@bogon:~/linuxapinew$ TZ="UTC"  ./a.out              
ctime() is:Wed Dec 28 11:16:01 2016
asmtime is:Wed Dec 28 11:16:01 2016

程式碼如下:

點選(此處)摺疊或開啟

  1. /*************************************************************************
  2.     > File Name: timezone.c
  3.     > Author: gaopeng QQ:22389860 all right reserved
  4.     > Mail: gaopp_200217@163.com
  5.     > Created Time: Wed 28 Dec 2016 06:57:50 PM CST
  6.  ************************************************************************/

  7. #include<stdio.h>
  8. #include <time.h>
  9. #include <errno.h>


  10. int main(void)
  11. {
  12.         time_t t;
  13.         struct tm *loc;
  14.         char* ctc;
  15.         char* asc;

  16.         t = time(NULL);
  17.         ctc = ctime(&t);
  18.         if ((loc = localtime(&t)) ==NULL)
  19.         {
  20.                 perror("localtime:");
  21.         }

  22.         asc = asctime(loc);

  23.         printf("ctime() is:%sasmtime is:%s",ctc,asc);
  24.         return 0;

  25. }


來自 “ ITPUB部落格 ” ,連結:http://blog.itpub.net/14710393/viewspace-2131123/,如需轉載,請註明出處,否則將追究法律責任。

相關文章