日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當(dāng)前位置: 首頁 > 运维知识 > 数据库 >内容正文

数据库

多数据库支持的应用程序设计(来自深空老大)

發(fā)布時(shí)間:2024/4/11 数据库 27 豆豆
生活随笔 收集整理的這篇文章主要介紹了 多数据库支持的应用程序设计(来自深空老大) 小編覺得挺不錯(cuò)的,現(xiàn)在分享給大家,幫大家做個(gè)參考.

2019獨(dú)角獸企業(yè)重金招聘Python工程師標(biāo)準(zhǔn)>>>

以前做PHP應(yīng)用,多數(shù)是單數(shù)據(jù)庫數(shù)據(jù)查詢和更新,頂多也是主從數(shù)據(jù)庫的支持,實(shí)現(xiàn)起來相對(duì)簡單。主從數(shù)據(jù)庫的問題在于,當(dāng)會(huì)話存儲(chǔ)在數(shù)據(jù)庫的時(shí)候,同步將可能出現(xiàn)問題,也就是說有可能出現(xiàn)會(huì)話的中斷。所以我想在主從數(shù)據(jù)庫設(shè)計(jì)上,應(yīng)該將所有會(huì)話相關(guān)表進(jìn)行特殊對(duì)待。即:所有的會(huì)話數(shù)據(jù)表都可以更新和查詢,當(dāng)一個(gè)用戶訪問站點(diǎn)的時(shí)候,即將此用戶綁定到指定數(shù)據(jù)庫,所有會(huì)話訪問和查詢操作都對(duì)此數(shù)據(jù)庫進(jìn)行。會(huì)話表不做同步,其他非會(huì)話類更新也從主數(shù)據(jù)庫更新。這樣做其實(shí)也逃脫不了會(huì)話更新時(shí)候的數(shù)據(jù)庫切換,所以如果不想麻煩,還是將會(huì)話存放在文本中進(jìn)行的好。
分?jǐn)?shù)據(jù)庫設(shè)計(jì),將可能從壓力性能上會(huì)提升幾個(gè)檔次,當(dāng)然單次執(zhí)行效率不會(huì)比單數(shù)據(jù)庫來的高的,畢竟存在著數(shù)據(jù)庫切換的效率問題。分庫以及主從數(shù)據(jù)庫搭配是可以比較好改善數(shù)據(jù)庫并發(fā)瓶頸的方案。原則:大數(shù)據(jù)量,分庫;大訪問量,主從。很多時(shí)候,都是這兩者并行(本文不討論cache)。
我想,如果要實(shí)現(xiàn)分庫以及主從關(guān)系,那么數(shù)據(jù)庫服務(wù)器數(shù)量將是非常可觀,在應(yīng)用程序中隨時(shí)切換到某一臺(tái)服務(wù)器,將是非常頭痛的問題,配置更換,變量名稱,是不是會(huì)有一大堆呢?如何尋找更好的解決方案將是本文談?wù)摰脑掝}。
首先是分庫使得數(shù)據(jù)庫頗多的問題。什么情況下分庫?或許有些人還搞不明白為什么要分庫,我就簡要說一下自己的經(jīng)驗(yàn)猜測(cè)。比如一個(gè)博客程序,一般設(shè)計(jì)是將日志存放在一張日志表中。假設(shè)是一個(gè)多用戶博客,那么將會(huì)關(guān)聯(lián)一個(gè)uid,如果數(shù)據(jù)量不大,這樣設(shè)計(jì)是沒有問題的,但是當(dāng)日志量巨大,一天有幾十萬條日志記錄錄入的時(shí)候,而且訪問量也比較可觀的時(shí)候,我想不可能每個(gè)用戶來訪問日志列表,都去從這包含幾千萬條日志記錄的數(shù)據(jù)表中去找那么幾條,效率可見一斑。這個(gè)時(shí)候就該考慮到分庫的問題。如何分?有一個(gè)很簡單的分表方法,即,根據(jù)uid段,將日志記錄在各個(gè)數(shù)據(jù)庫中,當(dāng)然,這個(gè)分布還是需要根據(jù)以往統(tǒng)計(jì)結(jié)果做出調(diào)整的,因?yàn)橛脩羧罩痉植伎隙ú皇蔷鶆虻摹TO(shè)置好uid段,然后根據(jù)uid索引到指定數(shù)據(jù)庫配置,創(chuàng)建一個(gè)數(shù)據(jù)庫對(duì)象即可。配置信息可能如下:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 $configs [ 'db_info' ][ 'blog' ][0] = array ( ???? 'db_host' => '192.168.0.1' , ???? 'db_name' => 'blog' , ???? 'db_user' => 'root' , ???? 'db_pass' => '' , ); $configs [ 'db_info' ][ 'blog' ][1] = array ( ???? 'db_host' => '192.168.0.2' , ???? 'db_name' => 'blog' , ???? 'db_user' => 'root' , ???? 'db_pass' => '' , ); $configs [ 'db_info' ][ 'blog' ][2] = array ( ???? 'db_host' => '192.168.0.2' , ???? 'db_name' => 'blog' , ???? 'db_user' => 'root' , ???? 'db_pass' => '' , ); //...還有很多

至于選擇哪一臺(tái)服務(wù)器,只需要根據(jù)uid做一個(gè)簡單的匹配就可以了。
再談到的就是主從數(shù)據(jù)庫了。什么情況下使用主從數(shù)據(jù)庫?比如某個(gè)名人博客,訪問量相當(dāng)?shù)拇?#xff0c;已經(jīng)沒有辦法把他的數(shù)據(jù)再進(jìn)行拆分了,這個(gè)時(shí)候就得考慮主從數(shù)據(jù)庫服務(wù)器了,使用多臺(tái)數(shù)據(jù)庫來分流。這樣要適用主從和分庫,可能上面配置信息得稍微改動(dòng)一下。

1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 $configs [ 'db_info' ][ 'blog' ][0][ 'master' ] = array ( ???? 'db_host' => '192.168.0.1' , ???? 'db_name' => 'blog' , ???? 'db_user' => 'root' , ???? 'db_pass' => '' , ); $configs [ 'db_info' ][ 'blog' ][0][ 'slave' ][0] = array ( ???? 'db_host' => '192.168.0.2' , ???? 'db_name' => 'blog' , ???? 'db_user' => 'root' , ???? 'db_pass' => '' , ); $configs [ 'db_info' ][ 'blog' ][0][ 'slave' ][1] = array ( ???? 'db_host' => '192.168.0.3' , ???? 'db_name' => 'blog' , ???? 'db_user' => 'root' , ???? 'db_pass' => '' , ); $configs [ 'db_info' ][ 'blog' ][1][ 'master' ] = array ( ???? 'db_host' => '192.168.0.4' , ???? 'db_name' => 'blog' , ???? 'db_user' => 'root' , ???? 'db_pass' => '' , ); $configs [ 'db_info' ][ 'blog' ][1][ 'slave' ][0] = array ( ???? 'db_host' => '192.168.0.5' , ???? 'db_name' => 'blog' , ???? 'db_user' => 'root' , ???? 'db_pass' => '' , ); $configs [ 'db_info' ][ 'blog' ][1][ 'slave' ][1] = array ( ???? 'db_host' => '192.168.0.6' , ???? 'db_name' => 'blog' , ???? 'db_user' => 'root' , ???? 'db_pass' => '' , ); $configs [ 'db_info' ][ 'session' ][0][ 'master' ] = array ( ???? 'db_host' => '192.168.0.7' , ???? 'db_name' => 'session' , ???? 'db_user' => 'root' , ???? 'db_pass' => '' , ); $configs [ 'db_info' ][ 'session' ][1][ 'master' ] = array ( ???? 'db_host' => '192.168.0.8' , ???? 'db_name' => 'session' , ???? 'db_user' => 'root' , ???? 'db_pass' => '' , );

寫到這里,我想都應(yīng)該知道如何分表和分配你的數(shù)據(jù)庫了吧,接下去我就來說一下如何輕松的讀取這樣的配置信息,如何將這些配置融入你的數(shù)據(jù)庫驅(qū)動(dòng)中。首先以單例摸式創(chuàng)建DB類:

1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 <?php if (!defined( "DB_FETCH_ASSOC" )) { ???? define( "DB_FETCH_ASSOC" , 1); } ?? if (!defined( "DB_FETCH_ROW" )) { ???? define( "DB_FETCH_ROW" , 2); } ?? if (!defined( "DB_FETCH_ARRAY" )) { ???? define( "DB_FETCH_ARRAY" , 3); } ?? if (!defined( "DB_FETCH_DEFAULT" )) { ???? define( "DB_FETCH_DEFAULT" , DB_FETCH_ASSOC); } class DB { ???? function DB( $dsn , $db_key , $p_conn , $fetch_mode ) { ???????? $this ->dsn??????? = $dsn ; ???????? $this ->db_key???? = $db_key ; ???????? $this ->sql??????? = '' ; ???????? $this ->sqls?????? = array (); ???????? $this ->u_sqls???? = array (); ???????? $this ->q_sqls???? = array (); ???????? $this ->u_conn???? = null; ???????? $this ->q_conn???? = null; ???????? $this ->p_conn???? = $p_conn ; ???????? $this ->fecth_mode = $fetch_mode ; ???????? $this ->query_num? = 0; ???????? $this ->update_num = 0; ???? } ?? ???? function &init(& $dsn , $db_key , $p_conn = false, $fetch_mode = DB_FETCH_DEFAULT) { ???????? static $db ; ???????? $db_key = explode ( '.' , $db_key ); ???????? $db_key = "['" . implode( "']['" , $db_key ) . "']" ; ???????? eval ( '$flag = isset($db' . $db_key . ');' ); ???????? eval ( "$db_info = $dsn['db_info']" . $db_key . ";" ); ???????? if (! $flag ) { ???????????? $obj = new DB( $db_info , $db_key , $p_conn , $fetch_mode ); ???????????? eval ( '$db' . $db_key . ' = $obj;' ); ???????????? unset( $obj ); ???????? } ???????? return $db ; ???? } } $db = &DB::init( $configs , 'blog.0' ); print_r( $db ); ?>

從上面打印結(jié)果可以看出,blog數(shù)據(jù)庫集群的第一組數(shù)據(jù)庫服務(wù)器被載入到$this->dsn中了。這個(gè)下面就是簡單的數(shù)據(jù)COPY的主從服務(wù)器,所以可以使用隨機(jī)數(shù)來指定到某一臺(tái)服務(wù)器。以下是一個(gè)簡單的隨機(jī)數(shù)實(shí)現(xiàn):

1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 class DB { ???? //.... ?? ???? function connectDB( $type = "master" ) { ???????? if ( $type == "master" ) { ???????????? $db_host = $this ->dsn[ "master" ][ "db_host" ]; ???????????? $db_name = $this ->dsn[ "master" ][ "db_name" ]; ???????????? $db_user = $this ->dsn[ "master" ][ "db_user" ]; ???????????? $db_pass = $this ->dsn[ "master" ][ "db_pass" ]; ???????????? $this ->u_conn = mysqli_connect( $db_host , $db_user , $db_pass ); ???????????? $this ->selectDB( $db_name , $this ->conn); ???????????? if (! $this ->u_conn) { ???????????????? $message = "Update DataBase Connect False : ($db_host, $db_user, ******) !" ; ???????????????? $this ->error( $message , 0); ???????????? } ???????? } else { ???????????? if ( empty ( $_COOKIE [ $_configs [ 'cookie_prefix' ] . 'db_no' ])) { ???????????????? $db_no = array_rand ( $this ->dsn[ "db_info" ][ "slave" ]); ???????????? } else { ???????????????? $db_no = $_COOKIE [ $_configs [ 'cookie_prefix' ] . 'db_no' ]; ???????????? } ???????????? $db_info = $this ->dsn[ "slave" ][ $db_no ]; ???????????? $db_host = $db_info [ "db_host" ]; ???????????? $db_name = $db_info [ "db_name" ]; ???????????? $db_user = $db_info [ "db_user" ]; ???????????? $db_pass = $db_info [ "db_pass" ]; ???????????? $this ->q_conn = mysqli_connect( $db_host , $db_user , $db_pass ); ?? ???????????? if (! $this ->q_conn) { ???????????????? if (! $this ->u_conn) { ???????????????????? $this ->connectDB(); ???????????????? } ???????????????? $this ->q_conn = $this ->u_conn; ???????????????? if (! $this ->q_conn) { ???????????????????? $message = "Query DataBase Connect False : ($db_host, $db_user, ******) !" ; ???????????????????? $this ->error( $message , 0); ???????????????? } ???????????? } else { ???????????????? $this ->selectDB( $db_name , $this ->q_conn); ???????????? } ???????? } ???? } ?? ???? function selectDB( $db_name , $conn ) { ???????? if ( $db_name != null) { ???????????? if (! mysqli_select_db( $conn , $db_name )) { ???????????????? $code = mysqli_errno( $conn ); ???????????????? $message = mysqli_error( $conn ); ???????????????? $this ->error( $message , $code ); ???????????? } ???????????? return true; ???????? } ???????? return false; ???? } ?? ???? function query( $sql , $limit = 1, $quick = false) { ???????? if ( $limit != null) { ???????????? $sql = $sql . " LIMIT " . $limit ; ???????? } ???????? $this ->sqls[] = $sql ; ???????? $this ->q_sqls[] = $sql ; ???????? $this ->sql = $sql ; ?? ???????? if ( empty ( $this ->q_conn)) { ???????????? $this ->connectDB( "slave" ); ???????? } ???????? $this ->qrs = mysqli_query( $this ->q_conn, $sql , $quick ? MYSQLI_USE_RESULT : MYSQLI_STORE_RESULT); ???????? if (! $this ->qrs) { ???????????? $code = mysqli_errno( $this ->q_conn); ???????????? $message = mysqli_error( $this ->q_conn); ???????????? $this ->error( $message , $code ); ???????? } ???????? $this ->query_num++; ???????? return $this ->qrs; ???? } ?? ???? function update( $sql ) { ???????? $this ->sql = $sql ; ???????? $this ->sqls[] = $this ->sql; ???????? $this ->u_sqls[] = $this ->sql; ???????? if ( $this ->u_conn == null) { ???????????? $this ->connectDB( "master" ); ???????? } ?? ???????? $this ->urs = mysqli_query( $this ->u_conn, $sql , MYSQLI_USE_RESULT); ???????? $this ->update_num++; ?? ???????? if (! $this ->urs) { ???????????? return false; ???????? } else { ???????????? return true; ???????? } ???? } }

至此,基本框架已經(jīng)出來了,來看看調(diào)用方法:

1 2 3 4 5 6 7 8 9 10 11 12 13 14 <?php // 連接到第一組會(huì)話服務(wù)器 $db = &DB::init( $configs , 'session.0' ); //? 執(zhí)行一次查詢 $db [ 'session' ][0]->query( 'SELECT ...' ); ?? //? 再次連接BLOG服務(wù)器 $db = &DB::init( $configs , 'blog.1' ); //? 執(zhí)行一次更新 $db [ 'blog' ][1]->update( 'UPDATE ...' ); ?? //? 再次調(diào)用會(huì)話更新 $db [ 'session' ][0]->update( 'INSERT ...' ); ?>

轉(zhuǎn)載于:https://my.oschina.net/tenking/blog/28574

總結(jié)

以上是生活随笔為你收集整理的多数据库支持的应用程序设计(来自深空老大)的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網(wǎng)站內(nèi)容還不錯(cuò),歡迎將生活随笔推薦給好友。

主站蜘蛛池模板: 男人天堂导航 | av不卡一区二区三区 | 伊人久久亚洲 | 黄久久久| 无码人妻精品一区二区三区99不卡 | 在线免费播放 | 国产三级全黄 | 亚洲色婷婷一区二区三区 | 国产av无码专区亚洲av麻豆 | 九九福利视频 | 黑人一区二区三区四区五区 | 久久不卡日韩美女 | 国产日本亚洲 | 国产五月天婷婷 | 国产三级国产精品国产专区50 | 六月婷婷在线观看 | 暖暖成人免费视频 | 日韩青青草 | 久射久 | 日本污网站| 午夜h视频| 在线免费观看a视频 | 伊人涩涩| 久久黄色av | 毛片在线观看视频 | 青草成人免费视频 | 久久国产热 | 欧美丰满艳妇bbwbbw | 色婷婷av一区二区三区四区 | 调教一区二区 | 欧美久久久精品 | 在线播放av网址 | 人人看人人爽 | 少妇闺蜜换浪荡h肉辣文 | 涩涩视频在线观看免费 | 五月天综合激情网 | 免费精品视频一区二区三区 | 日本老小玩hd老少配 | 肉色超薄丝袜脚交一区二区图片 | 欧美精品三级 | 免费黄色在线播放 | 成人精品二区 | 精一区二区 | 久久久www成人免费无遮挡大片 | 黄视频免费看在线 | 欧美第十页 | 国产xxx在线 | 一本色道无码道dvd在线观看 | 美日韩精品视频 | 又黄又色又爽的视频 | 欧美国产一二三区 | 日韩视频一区二区在线观看 | 黄片毛片 | 欧美精品一级二级三级 | 亚洲一区二区免费看 | 日韩激情图片 | 国产精品视频在 | 少妇人妻精品一区二区三区 | 高跟鞋丝袜猛烈xxxx | 又黄又高潮的视频 | 黄色一级在线视频 | 丝袜理论片在线观看 | 黄色小视频免费观看 | 中文字幕码精品视频网站 | 九九久久国产精品 | 国产调教打屁股xxxx网站 | 日韩电影精品 | 69国产| 国产在线播放一区二区 | 国产精品成人免费精品自在线观看 | 视频一区免费 | 少妇av导航 | 国产在线观 | 天天干天天色综合 | 欧美操穴视频 | 伊人久久精品视频 | 免费中文字幕在线观看 | h片网站在线观看 | 久久国产91| 正在播放亚洲 | 欧美一区二区在线观看视频 | 95在线视频 | 天天操夜夜干 | 国产精品怡红院 | 91免费 看片 | 黑人巨大精品欧美黑寡妇 | 日韩美女中文字幕 | 色综合图区 | 日日噜噜噜夜夜爽爽狠狠视频97 | 女生扒开尿口 | 午夜国产福利在线观看 | 三度诱惑免费版电影在线观看 | 日韩精品久久久久久久电影99爱 | 羞羞动漫在线观看 | 国产专区一区 | 精品久久久久久久久久久久 | 精品福利片 | 一级毛片黄色 | 无码人妻少妇伦在线电影 |