linux安裝redis及phpredis環境配置


下載安裝包

  cd /home/redis/tar

   wget http://redis.googlecode.com/files/redis-2.4.17.tar.gz

   tar zxvf redis-2.4.17.tar.gz

   cd redis-2.4.17

   make 

   cd src 

   make install

   在該目錄會看到以下文件

    

redis-benchmark      壓力測試

redis-check-aof       檢查redis持久化命令文件的完整性

redis-check-dump   檢查redis持久化數據文件的完整性

redis-cli                  redis在linux上的客戶端

redis-sentinel          做集群用的

redis-server            linux上的服務端

將redis源碼目錄下的  src目錄里的 redis-cli和 redis-server 拷貝到工作目錄里.同時將源碼根目錄下的redis.conf 也拷貝到工作目錄里

mkdir -p /usr/local/redis

mkdir -p /usr/local/redis

cp /home/redis/tar/redis-2.4.17/redis.conf /usr/local/redis

cd /home/redis/tar/redis-2.4.17/src

cp mkreleasehdr.sh redis-benchmak redis-check-aof redis-check-dump redis-cli redis-server   /usr/local/redis

啟動redis服務器:

 cd /usr/local/redis

 vi ./redis.conf

把參數daemonize no 改為 daemonize yes

 ./redis-server redis.conf

查看redis 是否啟動成功

ps -ef | grep redis

netstat -tunpl |grep 6379

關閉redis

pkill redis-server

二. redis配置文件說明

/usr/local/redis/redis.conf

1 daemonize  no

默認情況下,redis 不是在后台運行的,如果需要在后台運行,把該項的值更改為yes

2 pidfile  /var/run/redis.pid

當Redis 在后台運行的時候,Redis 默認會把pid 文件放在/var/run/redis.pid,你可以配置到其他地址。當運行多個redis 服務時,需要指定不同的pid 文件和端口

3 port

監聽端口,默認為6379

4 #bind 127.0.0.1

指定Redis 只接收來自於該IP 地址的請求,如果不進行設置,那么將處理所有請求,在生產環境中為了安全最好設置該項。默認注釋掉,不開啟

5 timeout 0

設置客戶端連接時的超時時間,單位為秒。當客戶端在這段時間內沒有發出任何指令,那么關閉該連接

tcp-keepalive 0

指定TCP連接是否為長連接,"偵探"信號有server端維護。默認為0.表示禁用

7 loglevel notice

log 等級分為4 級,debug,verbose, notice, 和warning。生產環境下一般開啟notice

8 logfile stdout

配置log 文件地址,默認使用標准輸出,即打印在命令行終端的窗口上,也可以修改為日志文件對應的目錄地址

9 databases 16

設置數據庫的個數,可以使用SELECT 命令來切換數據庫。默認使用的數據庫是0號庫。默認16個庫

10

save 900 1

save 300 10

save 60 10000

保存數據快照的頻率,即將數據持久化到dump.rdb文件中的頻度。用來描述"在多少秒期間至少多少個變更操作"觸發snapshot數據保存動作

默認設置,意思是:

if(在60 秒之內有10000 個keys 發生變化時){

進行鏡像備份

}else if(在300 秒之內有10 個keys 發生了變化){

進行鏡像備份

}else if(在900 秒之內有1 個keys 發生了變化){

進行鏡像備份

}

11 stop-writes-on-bgsave-error yes

當持久化出現錯誤時,是否依然繼續進行工作,是否終止所有的客戶端write請求。默認設置"yes"表示終止,一旦snapshot數據保存故障,那么此server為只讀服務。如果為"no",那么此次snapshot將失敗,但下一次snapshot不會受到影響,不過如果出現故障,數據只能恢復到"最近一個成功點"

12 rdbcompression yes

在進行數據鏡像備份時,是否啟用rdb文件壓縮手段,默認為yes。壓縮可能需要額外的cpu開支,不過這能夠有效的減小rdb文件的大,有利於存儲/備份/傳輸/數據恢復

13 rdbchecksum yes

讀取和寫入時候,會損失10%性能

14 rdbchecksum yes

是否進行校驗和,是否對rdb文件使用CRC64校驗和,默認為"yes",那么每個rdb文件內容的末尾都會追加CRC校驗和,利於第三方校驗工具檢測文件完整性

14 dbfilename dump.rdb

鏡像備份文件的文件名,默認為 dump.rdb

15 dir ./

數據庫鏡像備份的文件rdb/AOF文件放置的路徑。這里的路徑跟文件名要分開配置是因為Redis 在進行備份時,先會將當前數據庫的狀態寫入到一個臨時文件中,等備份完成時,再把該臨時文件替換為上面所指定的文件,而這里的臨時文件和上面所配置的備份文件都會放在這個指定的路徑當中

16 # slaveof <masterip> <masterport>

設置該數據庫為其他數據庫的從數據庫,並為其指定master信息。

17 masterauth

當主數據庫連接需要密碼驗證時,在這里指定

18 slave-serve-stale-data yes

當主master服務器掛機或主從復制在進行時,是否依然可以允許客戶訪問可能過期的數據。在"yes"情況下,slave繼續向客戶端提供只讀服務,有可能此時的數據已經過期;在"no"情況下,任何向此server發送的數據請求服務(包括客戶端和此server的slave)都將被告知"error"

19 slave-read-only yes

slave是否為"只讀",強烈建議為"yes"

20 # repl-ping-slave-period 10

slave向指定的master發送ping消息的時間間隔(秒),默認為10

21 # repl-timeout 60

slave與master通訊中,最大空閑時間,默認60秒.超時將導致連接關閉

22 repl-disable-tcp-nodelay no

slave與master的連接,是否禁用TCP nodelay選項。"yes"表示禁用,那么socket通訊中數據將會以packet方式發送(packet大小受到socket buffer限制)。

可以提高socket通訊的效率(tcp交互次數),但是小數據將會被buffer,不會被立即發送,對於接受者可能存在延遲。"no"表示開啟tcp nodelay選項,任何數據都會被立即發送,及時性較好,但是效率較低,建議設為no

23 slave-priority 100

適用Sentinel模塊(unstable,M-S集群管理和監控),需要額外的配置文件支持。slave的權重值,默認100.當master失效后,Sentinel將會從slave列表中找到權重值最低(>0)的slave,並提升為master。如果權重值為0,表示此slave為"觀察者",不參與master選舉

24 # requirepass foobared

設置客戶端連接后進行任何其他指定前需要使用的密碼。警告:因為redis 速度相當快,所以在一台比較好的服務器下,一個外部的用戶可以在一秒鍾進行150K 次的密碼嘗試,這意味着你需要指定非常非常強大的密碼來防止暴力破解。

25 # rename-command CONFIG 3ed984507a5dcd722aeade310065ce5d    (方式:MD5('CONFIG^!'))

重命名指令,對於一些與"server"控制有關的指令,可能不希望遠程客戶端(非管理員用戶)鏈接隨意使用,那么就可以把這些指令重命名為"難以閱讀"的其他字符串

26 # maxclients 10000

 

限制同時連接的客戶數量。當連接數超過這個值時,redis 將不再接收其他連接請求,客戶端嘗試連接時將收到error 信息。默認為10000,要考慮系統文件描述符限制,不宜過大,浪費文件描述符,具體多少根據具體情況而定

27 # maxmemory <bytes>

redis-cache所能使用的最大內存(bytes),默認為0,表示"無限制",最終由OS物理內存大小決定(如果物理內存不足,有可能會使用swap)。此值盡量不要超過機器的物理內存尺寸,從性能和實施的角度考慮,可以為物理內存3/4。此配置需要和"maxmemory-policy"配合使用,當redis中內存數據達到maxmemory時,觸發"清除策略"。在"內存不足"時,任何write操作(比如set,lpush等)都會觸發"清除策略"的執行。在實際環境中,建議redis的所有物理機器的硬件配置保持一致(內存一致),同時確保master/slave中"maxmemory""policy"配置一致。

當內存滿了的時候,如果還接收到set 命令,redis 將先嘗試剔除設置過expire 信息的key,而不管該key 的過期時間還沒有到達。在刪除時,

將按照過期時間進行刪除,最早將要被過期的key 將最先被刪除。如果帶有expire 信息的key 都刪光了,內存還不夠用,那么將返回錯誤。這樣,redis 將不再接收寫請求,只接收get 請求。maxmemory 的設置比較適合於把redis 當作於類似memcached的緩存來使用。

28 # maxmemory-policy volatile-lru

內存不足"時,數據清除策略,默認為"volatile-lru"。

volatile-lru  ->對"過期集合"中的數據采取LRU(近期最少使用)算法.如果對key使用"expire"指令指定了過期時間,那么此key將會被添加到"過期集合"中。將已經過期/LRU的數據優先移除.如果"過期集合"中全部移除仍不能滿足內存需求,將OOM.
allkeys-lru ->對所有的數據,采用LRU算法
volatile-random ->對"過期集合"中的數據采取"隨即選取"算法,並移除選中的K-V,直到"內存足夠"為止. 如果如果"過期集合"中全部移除全部移除仍不能滿足,將OOM
allkeys-random ->對所有的數據,采取"隨機選取"算法,並移除選中的K-V,直到"內存足夠"為止
volatile-ttl ->對"過期集合"中的數據采取TTL算法(最小存活時間),移除即將過期的數據.
noeviction ->不做任何干擾操作,直接返回OOM異常
另外,如果數據的過期不會對"應用系統"帶來異常,且系統中write操作比較密集,建議采取"allkeys-lru"

29 # maxmemory-samples 3

默認值3,上面LRU和最小TTL策略並非嚴謹的策略,而是大約估算的方式,因此可以選擇取樣值以便檢查

29 appendonly no

默認情況下,redis 會在后台異步的把數據庫鏡像備份到磁盤,但是該備份是非常耗時的,而且備份也不能很頻繁。所以redis 提供了另外一種更加高效的數據庫備份及災難恢復方式。開啟append only 模式之后,redis 會把所接收到的每一次寫操作請求都追加到appendonly.aof 文件中,當redis 重新啟動時,會從該文件恢復出之前的狀態。但是這樣會造成appendonly.aof 文件過大,所以redis 還支持了BGREWRITEAOF 指令,對appendonly.aof 進行重新整理。如果不經常進行數據遷移操作,推薦生產環境下的做法為關閉鏡像,開啟appendonly.aof,同時可以選擇在訪問較少的時間每天對appendonly.aof 進行重寫一次。

另外,對master機器,主要負責寫,建議使用AOF,對於slave,主要負責讀,挑選出1-2台開啟AOF,其余的建議關閉

30 # appendfilename appendonly.aof

aof文件名字,默認為appendonly.aof

31 

# appendfsync always
appendfsync everysec
# appendfsync no

設置對appendonly.aof 文件進行同步的頻率。always 表示每次有寫操作都進行同步,everysec 表示對寫操作進行累積,每秒同步一次。no不主動fsync,由OS自己來完成。這個需要根據實際業務場景進行配置

32 no-appendfsync-on-rewrite no

在aof rewrite期間,是否對aof新記錄的append暫緩使用文件同步策略,主要考慮磁盤IO開支和請求阻塞時間。默認為no,表示"不暫緩",新的aof記錄仍然會被立即同步

33 auto-aof-rewrite-percentage 100

當Aof log增長超過指定比例時,重寫log file, 設置為0表示不自動重寫Aof 日志,重寫是為了使aof體積保持最小,而確保保存最完整的數據。

34 auto-aof-rewrite-min-size 64mb

觸發aof rewrite的最小文件尺寸

35 lua-time-limit 5000

lua腳本運行的最大時間

36 slowlog-log-slower-than 10000

"慢操作日志"記錄,單位:微秒(百萬分之一秒,1000 * 1000),如果操作時間超過此值,將會把command信息"記錄"起來.(內存,非文件)。其中"操作時間"不包括網絡IO開支,只包括請求達到server后進行"內存實施"的時間."0"表示記錄全部操作

37 slowlog-max-len 128

"慢操作日志"保留的最大條數,"記錄"將會被隊列化,如果超過了此長度,舊記錄將會被移除。可以通過"SLOWLOG <subcommand> args"查看慢記錄的信息(SLOWLOG get 10,SLOWLOG reset)

38

 hash-max-ziplist-entries 512

hash類型的數據結構在編碼上可以使用ziplist和hashtable。ziplist的特點就是文件存儲(以及內存存儲)所需的空間較小,在內容較小時,性能和hashtable幾乎一樣.因此redis對hash類型默認采取ziplist。如果hash中條目的條目個數或者value長度達到閥值,將會被重構為hashtable。

這個參數指的是ziplist中允許存儲的最大條目個數,,默認為512,建議為128
hash-max-ziplist-value 64

ziplist中允許條目value值最大字節數,默認為64,建議為1024

39 

list-max-ziplist-entries 512
list-max-ziplist-value 64

對於list類型,將會采取ziplist,linkedlist兩種編碼類型。解釋同上。

40 set-max-intset-entries 512

intset中允許保存的最大條目個數,如果達到閥值,intset將會被重構為hashtable

41 

zset-max-ziplist-entries 128
zset-max-ziplist-value 64

zset為有序集合,有2中編碼類型:ziplist,skiplist。因為"排序"將會消耗額外的性能,當zset中數據較多時,將會被重構為skiplist。

42 activerehashing yes

是否開啟頂層數據結構的rehash功能,如果內存允許,請開啟。rehash能夠很大程度上提高K-V存取的效率

43 

client-output-buffer-limit normal 0 0 0
client-output-buffer-limit slave 256mb 64mb 60
client-output-buffer-limit pubsub 32mb 8mb 60

客戶端buffer控制。在客戶端與server進行的交互中,每個連接都會與一個buffer關聯,此buffer用來隊列化等待被client接受的響應信息。如果client不能及時的消費響應信息,那么buffer將會被不斷積壓而給server帶來內存壓力.如果buffer中積壓的數據達到閥值,將會導致連接被關閉,buffer被移除。

buffer控制類型包括:normal -> 普通連接;slave ->與slave之間的連接;pubsub ->pub/sub類型連接,此類型的連接,往往會產生此種問題;因為pub端會密集的發布消息,但是sub端可能消費不足.
指令格式:client-output-buffer-limit <class> <hard> <soft> <seconds>",其中hard表示buffer最大值,一旦達到閥值將立即關閉連接;
soft表示"容忍值",它和seconds配合,如果buffer值超過soft且持續時間達到了seconds,也將立即關閉連接,如果超過了soft但是在seconds之后,buffer數據小於了soft,連接將會被保留.
其中hard和soft都設置為0,則表示禁用buffer控制.通常hard值大於soft.

44 hz 10

Redis server執行后台任務的頻率,默認為10,此值越大表示redis對"間歇性task"的執行次數越頻繁(次數/秒)。"間歇性task"包括"過期集合"檢測、關閉"空閑超時"的連接等,此值必須大於0且小於500。此值過小就意味着更多的cpu周期消耗,后台task被輪詢的次數更頻繁。此值過大意味着"內存敏感"性較差。建議采用默認值。

45 

# include /path/to/local.conf
# include /path/to/other.conf

額外載入配置文件。

 phpredis擴展安裝

   phpredis中文手冊:

  http://www.cnblogs.com/ikodota/archive/2012/03/05/php_redis_cn.html

  下載phpredis

   https://github.com/owlient/phpredis

   cd /home/redis/tar

   tar phpredis.tar.gz

   cd phpredis.tar.gz

   /usr/local/php/bin/phpize    #此指令必須在phpredis解壓包/home/redis/tar/phpredis 執行

安裝autoconf-2.62.tar.gz

 cd /home/redis/tar

 tar zxvf autoconf-2.62.tar.gz

 cd autoconf-2.62

 ./configure && make && make install

  

  配置並編譯安裝phpredis

 ./configure --with-php-config=/usr/local/php/bin/php-config

  make && make install

  

 

nginx 為php安裝redis擴展
獲取源碼包
wget https://github.com/nicolasff/phpredis/archive/master.zip
或https://github.com/owlient/phpredis
unzip master.zip
cd phpredis-master/
/application/php/bin/phpize #如果是yum安裝php-devel 那么直接使用phpize
./configure --with-php-config=/usr/local/php/bin/php-config #如果是yum安裝的php 直接。、configure
make
make install
修改/etc/php.ini
添加
extension_dir ="/usr/lib64/php/modules/"
extension=redis.so
重啟php
/etc/init.d/php-fpm restart

 

 

 

給php.ini設置redis擴展

   打開php.ini配置文件設置以下代碼

   vi /usr/local/php/etc/php.ini

   

   重啟apache

   /usr/local/http2/bin/apachectl restart

查看php是否有引入redis擴展

 

php使用redis示例代碼

如果不清楚php-redis擴展內部到底有什么方法可以利用反射

String類型

set 設置key對應的值為string類型的value

get 獲取key對應的string值,如果key不存在返回nil

setnx 設置key對應的值為string類型的value 如果key已經存在 返回0,nx是not exist的意思

setex設置key對應的值為string類型的value 並指定此鍵值對應的有效期

例如:我們添加一個color=red的鍵值對並指定有效期為10秒

setrange 設置指定key的value值的子字符串

mset 一次設置多個key的值,成功返回ok表示所有的值都設置了,失敗返回0表示沒有任何值被設置

 

msetnx 一次設置多個key的值,成功返回ok表示所有的值都被設置了,失敗返回0表示沒有任何值被設置(其中的key已存在),不會覆蓋已存在的key

getset 設置key的值,並返回key的舊值

getrange獲取key的value值的子字符串

mget 一次獲取多個key的值,如果對應的key不存在則對應返回nil

 incr對key的值做加加操作,並返回新的值

incrby同incr類似,加指定的值,key不存在時候會設置key,並認為原來的value是0.

decr 對key的值做減減操作

decrby 同decr類似減指定的值

append 給指定key的字符串追加value,返回新字符串值的長度

strlen取指定key的value值的長度

hash類型

redis hash是一個string類型的field和value的映射表。它的添加 刪除操作都是0(1) hash特別適合用於存儲對象,相比較於將對象的每個字段存成string類型。將一個對象存儲在hash類型中會占用更少的內存。並且可以更方便的存取整個對象。

 hset設置hash field為指定值,如果key不存在則先創建

hsetnx設置hash field為指定值,如果key不存在,則先創建。如果存在返回0.

hmset 同時設置hash的多個field的值,設置成功返回ok

hget 獲取hash field的值

hmget 獲取全部指定的hash field field1 的值

hincrby 指定的hash field 加上給定的值

hexists 測試指定的field是否存在 如果存在返回1 否則返回0

hlen 返回指定hash的field數量

hdel 刪除指定hash的field

hkeys 返回hash的所有field

hvals 返回hash的所有value

hgetall獲取某個hash中全部的field及value

list類型

list是一個鏈表結構主要功能是push  pop 獲取一個范圍的所有值等等。操作中key理解為鏈表的名字。redis的list類型其實就是一個每個子元素都是string類型的雙向鏈表。我們可以通過push pop操作從鏈表的頭部或者尾部添加刪除元素。這樣list既可以作為棧,又可以作為隊列。

lpush 在key對應list的頭部添加字符串元素  先進后出原則

rpush 在key對應的list的尾部添加字符串元素   先進先出原則

linsert 在key對應list的特定位置前或后添加字符串

 

lset設置list中指定下標的元素值

lrem 從key對應的list中刪除n個和value相同的元素(n<0從尾刪除,n=0全部刪除)

ltrim 保留指定key的值范圍內的數據刪除其他的值

ltrim list1 1 -1 從下標1開始保留全部的數據 1 2 從下標1開始保留兩個數據

lpop從list的頭部刪除元素,並返回刪除元素

rpop從list的尾部刪除元素,並返回刪除元素

rpoplpush 從第一個list的尾部移除元素並添加到第二個list的頭部

lindex 返回名稱為key的list中index位置的元素

llen 返回key對應list的長度

 set類型

set是集合,它是string類型的無序集合。set是通過hash table實現的,添加,刪除和查找的復雜度都是0(1).對集合我們可以取並集,交集,差集。通過這些操作我們可以實現sns中的好友推薦和blog的tag功能

sadd 向名稱為key的set中添加元素

srem 刪除名稱為key的set中的元素

spop隨機返回並刪除名稱為key的set中一個元素

sdiff 返回所有給定key與第一個key的差集

sdiffstore返回所有給定key與第一個key的差集,並將結果存為另一個key

sinter 返回所有給定key的交集

sinterstore返回所有給定key的交集,並將結果存為另一個key

sunion 返回所有給定key的並集

sunionstore 返回所有給定key的並集並存儲為myset7

smove 從第一個key對應的set中移除member並添加到第二個對應的set中

scard 返回名稱為key的set的元素個數

sismember 測試member是否是名稱為key的set元素

srandmember 隨機返回名稱為key的set的一個元素,但不刪除元素

sorted set類型

sorted set是set的一個升級版本,它在set的基礎上增加一個順序屬性,這個屬性在添加修改元素的時候可以指定,每次指定后,zset會自動重新按新的值調整順序,可以理解為有兩列的mysql表,一列存value.一列存順序,操作key理解為zset的名字。

zadd向名稱為key的zset中添加元素member,score用於排序。如果該元素存在,則更新其順序。

zrang讀取zset中的值。withscores 取順序號

zrem刪除名稱為key的zset中的元素member

zincrby如果在名稱為key的zset中已經存在元素member,則該元素的score增加increment否則向該集合中添加該元素,其score的值為increment

zrank 返回zset集合value的索引值

zrevrank返回名稱為key的zset中member元素的排名(按score從大到小排序)即下標

zrevrange 返回名稱為key的zset(按score從大到小順序)中的index從start到end的所有元素

 

zrangebyscore 返回指定下標的值

 

zcount 返回集合中給定區間的數量

 

zcard 返回集合中元素的個數

zremrangebyrank 刪除集合中排名在給定區間的元素(按索引)

zremrangebyscore 刪除集合中score在給定區間的元素(按順序號)

 redids中鍵值相關命令

keys 返回滿足給定pattern的所有key  用表達式*,代表取出所有的key

exists 確認一個key是否存在 存在返回1 不存在返回0

del 刪除一個key

expire 設置一個key的過期時間  ttl 查看key的剩余過期時間 為-1 表示已經過期

select 是選擇數據庫   select 0  數據庫0-15

move 將當前數據庫中的key轉移到其他數據庫中

persist 移除給定key的過期時間

randomkey 隨機返回key空間的一個key

rename 重命名key

type 返回值的類型

服務器相關命令

ping 測試連接是否存活

quit或exit 退出連接

dbsize 返回當前數據庫中key的數目

info 獲取服務器的信息和統計

config get 實時存儲收到的請求

config get dir 獲取dir這個參數配置的值如果想獲取全部參數數據的 配置值也很簡單,只需要執行 config get *j

即可將全部值都顯示出來

flushdb 刪除當前選擇數據庫中的所有key

flushall 刪除所有數據庫中的所有key

 

redis高級使用特性

1.安全性

設置客戶端連接后進行任何其他指定前需要輸入密碼。

  因為redis速度相當快,所以在一台比較好的服務器下,一個外部的用戶可以在一秒鍾進行150k次的密碼嘗試。這意味着你需要指定非常非常強大的密碼來防止暴力破解。

 vi  /usr/local/redis/redis.conf

  添加 requirepass = ceshi

 

  pkill redis-server

  重啟redis

 /usr/local/redis/redis-server  /usr/local/redis/redis.conf

 /usr/local/redis/redis-cli -a ceshi

 auth mima 設置權限  就是登陸客戶端的時候沒有指定 -a

 

 

redis主從復制過程

 1.slave與master建立連接,發送sync同步命令

 2、master會啟動一個后台進程,將數據庫快照保存到文件中,同時master主進程會開始收集新的寫命令並緩存。

 3、后台完成保存后,就將此文件發送給slave

 4、slave將此文件保存到硬盤上

配置主從服務器:

 配置slave服務器很簡單,只需要在slave的配置文件中加入以下配置:

 slaveof 192.168.1.1 6379 #指定master的ip和端口

 masterauth ceshi #這是主機的密碼

在redis_slave 服務器的/usr/local/redis/redis.conf

重啟redis_slave服務的redis

redis對事務的支持目前還比較簡單。redis只能保證一個client發起的事務中的命令可以連續的執行。而中間不會插入其他client的命令。當一個client在一個連接中發出multi命令時。這個連接會進入一個事務上下文,該連接后續的命令不會立即執行,而是先放到一個隊列中,當執行exec命令時,redis會順序的執行隊列中的所有命令。

discard 取消事務

當事務中任何一個出錯 但redis的事務不會全部回滾

樂觀鎖復雜事務控制

redis 持久化機制

redis是一個支持持久化的內存數據庫,也就是說redis需要經常將內存中的數據同步到硬盤來保證持久化

1.snapshotting(快照)也是默認方式

2.Append-onlyfile(縮寫aof)的方式

配置文件中添加 relly-use-vm yes

 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM