HAProxy:基礎詳解

一、簡介

HAProxy提供高可用性、負載均衡以及基於TCP和HTTP應用的代理,支持虛擬主機,它是免費、快速並且可靠的一種解決方案。HAProxy特別適用於那些負載特大的web站點,這些站點通常又需要會話保持或七層處理。HAProxy運行在時下的硬件上,完全可以支持數以萬計的併發連接。並且它的運行模式使得它可以很簡單安全的整合進您當前的架構中, 同時可以保護你的web服務器不被暴露到網絡上。

HAProxy實現了一種事件驅動、單一進程模型,此模型支持非常大的併發連接數。多進程或多線程模型受內存限制 、系統調度器限制以及無處不在的鎖限制,很少能處理數千併發連接。事件驅動模型因爲在有更好的資源和時間管理的用戶端(User-Space) 實現所有這些任務,所以沒有這些問題。此模型的弊端是,在多核系統上,這些程序通常擴展性較差。這就是爲什麼他們必須進行優化以 使每個CPU時間片(Cycle)做更多的工作。

二、配置文件格式

配置文件中的參數具體參考:http://cbonte.github.io/haproxy-dconv/configuration-1.4.html

配置文件格式:

全局參數:

global
    # to have these messages end up in /var/log/haproxy.log you will
    # need to:
    #
    # 1) configure syslog to accept network log events.  This is done
    #    by adding the '-r' option to the SYSLOGD_OPTIONS in
    #    /etc/sysconfig/syslog
    #
    # 2) configure local2 events to go to the /var/log/haproxy.log
    #   file. A line like the following can be added to
    #   /etc/sysconfig/syslog
    #
    #    local2.*                       /var/log/haproxy.log
    #
    log         127.0.0.1 local2            #定義日誌的,需要在syslog中開啓
    chroot      /var/lib/haproxy            #指定haproxy工作目錄,能提高安全性
    pidfile     /var/run/haproxy.pid        #pid文件文職
    maxconn     40000                       #最大併發連接數
    user        haproxy                     #指定用戶運行haproxy
    group       haproxy
    daemon                                  #以守護進程方式工作於後臺
    # turn on stats unix socket
    stats socket /var/lib/haproxy/stats     #

代理相關配置主要分爲四段:

  • defaults <name>:用於爲所有其它配置段提供默認參數,這配置默認配置參數可由下一個“defaults”所重新設定。

defaults
    mode                    http            #指定協議
    log                     global          #指定日誌是從全局繼承
    option                  httplog         #開啓日誌記錄http請求等信息
    option                  dontlognull     #啓用或禁用日誌記錄空連接
    option http-server-close  #在支持保持連接的情況下;一旦用戶的保持連接超時;是否允許服務器發起關閉.
    option forwardfor       except 127.0.0.0/8 #允許在request 中加入X-Forwarded-For header 發往server
    option                  redispatch      #基於cookie的會話保持時;一旦upstream server宕機時;將此server的會話重新定向到其他的upstream server;
    retries                 3               #重試次數
    timeout http-request    10s             #關閉客戶端一次性請求的時長
    timeout queue           1m              #在隊列中等待時間
    timeout connect         10s             #定義haproxy將用戶請求轉發後端upstream server時的超時時長
    timeout client          1m              #客戶端非活動連接的超時時長
    timeout server          1m              #等待服務器端非活動連接的超時時長
    timeout http-keep-alive 10s             #設置保持連接模式的超時時長
    timeout check           10s             #檢查請求建立後;服務器端沒有響應的超時時長
    maxconn                 3000            #每個server默認最大連接數
  • frontend <name>:用於定義一系列監聽的套接字,這些套接字可接受客戶端請求並與之建立連接。

#---------------------------------------------------------------------
# main frontend which proxys to the backends
#---------------------------------------------------------------------
frontend  main *:5000    #定義前端的監聽地址和端口
    acl url_static       path_beg       -i /static /p_w_picpaths /javascript /stylesheets
#定義訪問控制列表,上述含義是以後面參數開頭path的且不區分大小寫爲url_static列表
    acl url_static       path_end       -i .jpg .gif .png .css .js
#同上
    use_backend static          if url_static
#如果匹配到url_static列表,則代理至backend定義的static server
    default_backend             app
#否則,默認到app server
  • backend <name>:用於定義一系列“後端”服務器,代理將會將對應客戶端的請求轉發至這些服務器。

backend static    #定義後端server
    balance     roundrobin    算法rr
    server      static 127.0.0.1:4331 check    #check代表健康檢測
#---------------------------------------------------------------------
# round robin balancing between the various backends
#---------------------------------------------------------------------
backend app
    balance     roundrobin
    server  app1 127.0.0.1:5001 check
    server  app2 127.0.0.1:5002 check
    server  app3 127.0.0.1:5003 check
    server  app4 127.0.0.1:5004 check
  • listen <name>:通過關聯“前端”和“後端”定義了一個完整的代理,通常只對TCP流量有用。

三、配置文件中部分關鍵字

1、acl訪問控制列表

acl <aclname> <criterion> [flags] [operator] <value> ...

  • <aclname>:ACL名稱,區分字符大小寫,且其只能包含大小寫字母、數字、-(連接線)、_(下劃線)、.(點號)和:(冒號);haproxy中,acl可以重名,這可以把多個測試條件定義爲一個共同的acl;

  • <criterion>:測試標準,即對什麼信息發起測試;測試方式可以由[flags]指定的標誌進行調整;而有些測試標準也可以需要爲其在<value>之前指定一個操作符[operator];

  • [flags]:目前haproxy的acl支持的標誌位有3個:

    -i:不區分<value>中模式字符的大小寫;

    -f:從指定的文件中加載模式;

    --:標誌符的強制結束標記,在模式中的字符串像標記符時使用;

  • <value>:acl測試條件支持的值有以下四類:

    - integers or integer ranges:整數或整數範圍:如1024:65535表示從1024至65535;且支持使用的操作符有5個,分別爲eq、ge、gt、le和lt;

    - strings:支持使用“-i”以忽略字符大小寫,支持使用“\”進行轉義;如果在模式首部出現了-i,可以在其之前使用“--”標誌位;

    - regular expressions:正則表達式:其機制類同字符串匹配;

    - IP addresses and networks:IP地址及網絡地址;

常用的測試標準:

  • be_sess_rate(backend) <integer>:用於測試指定的backend上會話創建的速率(即每秒創建的會話數)是否滿足指定的條件;常用於在指定backend上的會話速率過高時將用戶請求轉發至另外的backend,或用於阻止***行爲。

  • fe_sess_rate(frontend) <integer>:用於測試指定的frontend(或當前frontend)上的會話創建速率是否滿足指定的條件;常用於爲frontend指定一個合理的會話創建速率的上限以防止服務被濫用。

  • hdr(header) <string>:用於測試請求報文中的所有首部或指定首部是否滿足指定的條件;指定首部時,其名稱不區分大小寫,且在括號“()”中不能有任何多餘的空白字符。測試服務器端的響應報文時可以使用shdr()。

  • method <string>:測試HTTP請求報文中使用的方法。

  • path_beg <string>:用於測試請求的URL是否以<string>指定的模式開頭。

  • path_end <string>:用於測試請求的URL是否以<string>指定的模式結尾。

  • hdr_beg <string>:用於測試請求報文的指定首部的開頭部分是否符合<string>指定的模式。

  • hdr_end <string>:用於測試請求報文的指定首部的結尾部分是否符合<string>指定的模式。

2、balance格式:

balance <algorithm> [ <arguments> ]

balance url_param <param> [check_post [<max_wait>]]

定義負載均衡算法,可用於“defaults”、“listen”和“backend”。<algorithm>用於在負載均衡場景中挑選一個server,其僅應用於持久信息不可用的條件下或需要將一個連接重新派發至另一個服務器時。

調度算法:

  • roundrobin:基於權重進行輪叫,在服務器的處理時間保持均勻分佈時,這是最平衡、最公平的算法。此算法是動態的,這表示其權重可以在運行時進行調整生效。

  • static-rr:基於權重進行輪叫,與roundrobin類似,但是爲靜態方法,在運行時調整其服務器權重不會生效;不過,其在後端服務器連接數上沒有限制。

  • leastconn:新的連接請求被派發至具有最少連接數目的後端服務器;在有着較長時間會話的場景中推薦使用此算法,如LDAP、SQL等,其並不太適用於較短會話的應用層協議,如HTTP;此算法是動態的,可以在運行時調整其權重。

  • source:sh算法,並由後端服務器的權重總數相除後派發至某匹配的服務器;這可以使得同一個客戶端IP的請求始終被派發至某特定的服務器;不過,當服務器權重總數發生變化時,如某服務器宕機或添加了新的服務器,許多客戶端的請求可能會被派發至與此前請求不同的服務器;常用於負載均衡無cookie功能的基於TCP的協議;其默認爲靜態,不過也可以使用hash-type修改此特性;

  • uri:對URI的左半部分(“問題”標記之前的部分)或整個URI進行hash運算,並由服務器的總權重相除後派發至某匹配的服務器;這可以使得對同一個URI的請求總是被派發至某特定的服務器,除非服務器的權重總數發生了變化;此算法常用於代理緩存或反病毒代理以提高緩存的命中率;需要注意的是,此算法僅應用於HTTP後端服務器場景;其默認爲靜態算法,不過也可以使用hash-type修改此特性;

  • url_param:通過<argument>爲URL指定的參數在每個HTTP GET請求中將會被檢索;如果找到了指定的參數且其通過等於號“=”被賦予了一個值,那麼此值將被執行hash運算並被服務器的總權重相除後派發至某匹配的服務器;此算法可以通過追蹤請求中的用戶標識進而確保同一個用戶ID的請求將被送往同一個特定的服務器,除非服務器的總權重發生了變化;如果某請求中沒有出現指定的參數或其沒有有效值,則使用輪叫算法對相應請求進行調度;此算法默認爲靜態的,不過其也可以使用hash-type修改此特性;

  • hdr(<name>):對於每個HTTP請求,通過<name>指定的HTTP首部將會被檢索;如果相應的首部沒有出現或其沒有有效值,則使用輪叫算法對相應請求進行調度;其有一個可選選項“use_domain_only”,可在指定檢索類似Host類的首部時僅計算域名部分(比如通過www.magedu.com來說,僅計算magedu字符串的hash值)以降低hash算法的運算量;此算法默認爲靜態的,不過其也可以使用hash-type修改此特性;

  • rdp-cookie(name)/rdp-cookie:爲每個進來的TCP請求查詢並哈希RDP cookie <name> (或“mstshash”如果省略) 。與ACL函數 'req_rdp_cookie()'一樣,name不區分大小寫。該機制用於退化的持久模式,可以使同一個用戶(或同一個會話ID)總是發送給同一臺服務器。如果沒有cookie, 則使用roundrobin算法代替。

3、mode { tcp|http|health }:設定啓動的實例的協議類型。

4、errorfile <code> <file>:在用戶請求不存在的頁面時,返回一個頁面文件給客戶端而非由haproxy生成的錯誤代碼;可用於所有段中。

5、server <name> <address>[:port] [param*]:爲後端聲明一個server,因此,不能用於defaults和frontend區段。

<name>:爲此服務器指定的內部名稱,其將出現在日誌及警告信息中;如果設定了"http-send-server-name",它還將被添加至發往此服務器的請求首部中;

[param*]:爲此服務器設定的一系參數;其可用的參數非常多,具體請參考官方文檔中的說明,下面僅說明幾個常用的參數;

參數說明:

  • backup:設定爲備用服務器,僅在負載均衡場景中的其它server均不可用於啓用此server;

  • check:啓動對此server執行健康狀態檢查,其可以藉助於額外的其它參數完成更精細的設定:

    inter <delay>:設定健康狀態檢查的時間間隔,單位爲毫秒,默認爲2000;也可以使用fastinter和downinter來根據服務器端狀態優化此時間延遲;

    rise <count>:設定健康狀態檢查中,某離線的server從離線狀態轉換至正常狀態需要成功檢查的次數;

    fall <count>:確認server從正常狀態轉換爲不可用狀態需要檢查的次數;

  • cookie <value>:爲指定server設定cookie值,此處指定的值將在請求入站時被檢查,第一次爲此值挑選的server將在後續的請求中被選中,其目的在於實現持久連接的功能;

  • maxconn <maxconn>:指定此服務器接受的最大併發連接數;如果發往此服務器的連接數目高於此處指定的值,其將被放置於請求隊列,以等待其它連接被釋放;

  • maxqueue <maxqueue>:設定請求隊列的最大長度;

  • observe <mode>:通過觀察服務器的通信狀況來判定其健康狀態,默認爲禁用,其支持的類型有“layer4”和“layer7”,“layer7”僅能用於http代理場景;

  • redir <prefix>:啓用重定向功能,將發往此服務器的GET和HEAD請求均以302狀態碼響應;需要注意的是,在prefix後面不能使用/,且不能使用相對地址,以免造成循環;

  • weight <weight>:權重,默認爲1,最大值爲256,0表示不參與負載均衡

6、haproxy的狀態信息stats

  • stats enable:默認設置下啓用狀態信息頁面;

  • stats hide-version:啓用統計報告並隱藏HAProxy版本報告,不能用於“frontend”區段。

  • stats realm <realm>:統計頁面密碼框上提示文本,不能用於“frontend”區段。

  • stats refresh <delay>:啓用統計頁面的自動刷新功能。

  • stats scope { <name> | "." }:啓用統計報告並限定報告的區段,不能用於“frontend”區段

    <name>:可以是一個“listen”、“frontend”或“backend”區段的名稱,而“.”則表示stats scope語句所定義的當前區段。

  • stats auth <user>:<passwd>:啓用帶認證的統計報告功能並授權一個用戶帳號,其不能用於“frontend”區段。

  • stats admin { if | unless } <cond>:在指定的條件滿足時啓用統計報告頁面的管理級別功能,它允許通過web接口啓用或禁用服務器

配置實例:

backend web
  server websrv1 192.168.0.111:80
  stats enable
  stats hide-version
  stats scope   .
  stats uri     /.admin?stats
  stats realm   Haproxy\ Statistics
  stats auth    administrator:password
  stats auth    master:password
  stats admin if TRUE

wKiom1Nh5dbz88o0AAN1gnaWX6E963.jpg

配置後測試登陸。

haproxy的配置文件格式及一些基本的參數以詳細說明;具體的可用根據給定的官方文檔做參照。





如有錯誤;懇請更正。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章