Apache จะผสานหลายส่วนในตำแหน่งที่ตรงกันได้อย่างไร


34

ฉันกำลังทำงานกับการกำหนดค่า apache พื้นฐานบางอย่าง แต่ฉันไม่เข้าใจอย่างชัดเจนว่า apache ผสาน<Location>ส่วนต่างๆ อย่างไรเมื่อมีหลายรายการที่ตรงกับ URL คำขอที่เข้ามา เอกสาร Apacheใน "วิธีส่วนจะถูกผสาน" บทนิด ๆ หน่อย ๆ ทำให้เกิดความสับสนเมื่อมันมาถึงการสั่งซื้อ / จัดลำดับความสำคัญของหลายส่วนการจับคู่ของประเภทเดียวกัน

ตัวอย่างเช่นลองนึกภาพการตั้งค่า apache ต่อไปนี้ (ไม่สนใจว่าเนื้อหาจริงเหมาะสมหรือไม่ฉันสนใจเพียงลำดับของแต่ละกฎ / ส่วน):

<Location / >
  ProxyPass http://backend.com/
  Order allow,deny
  Satisfy any
</Location>

<Location /sub/foo>
  Order allow,deny
</Location>

<Location /sub >
  Order deny,allow
  Require valid-user
  Satisfy all
</Location>

<Location /doesnt/match >
  ProxyPass !
</Location>

ตอนนี้หากลูกค้าทำการร้องขอ/sub/foobarซึ่งเป็นการกำหนดค่าสุดท้ายที่จะนำไปใช้กับการร้องขอนี้?

การกำหนดค่าที่ใช้มีค่าเท่ากับ:

# All the directives contained in all the matchin Locations in declaration order
ProxyPass http://backend.com/
Order allow,deny
Satisfy any
Order allow,deny
Order deny,allow
Require valid-user
Satisfy all

หรืออาจจะ

# same as above, but with longest matching path last
ProxyPass http://backend.com/
Order allow,deny
Satisfy any
Order deny,allow
Require valid-user
Satisfy all
Order allow,deny

หรือสิ่งที่แตกต่างอย่างสิ้นเชิง

ขอบคุณสำหรับความช่วยเหลือของคุณฉันสับสนจริงๆ

คำตอบ:


43

ลำดับของการรวมค่อนข้างซับซ้อนและง่ายต่อการตรวจสอบโดยข้อยกเว้น ... apache doc คือ " วิธีการรวมส่วนต่างๆ "

ตามเอกสารประกอบนั้นลำดับของการรวมส่วนทำได้โดยการประมวลผลรายการที่ตรงกันทั้งหมดสำหรับแต่ละประเภทการจับคู่ตามลำดับที่พบในไฟล์กำหนดค่าจากนั้นย้ายไปยังประเภทถัดไป (ยกเว้น <Directory > ซึ่งได้รับการปฏิบัติตามลำดับความจำเพาะของเส้นทาง)

คำสั่งของประเภทคือDirectory, DirectoryMatch, และในที่สุดก็Files Locationการแข่งขันในภายหลังจะเขียนทับการแข่งขันก่อนหน้า (* ProxyPass และ Alias ​​ได้รับการปฏิบัติต่างกันอีกครั้งโปรดดูหมายเหตุท้าย)

และมีข้อยกเว้นที่สำคัญหลายประการสำหรับกฎเหล่านี้ที่ใช้กับการใช้ ProxyPass และ ProxyPass ในส่วน <Location> (ดูด้านล่าง)

ดังนั้นจากตัวอย่างของคุณด้านบนขอhttp://somehost.com/sub/foobarด้วย follwing config;

<Location / >
  ProxyPass http://backend.com/
  Order allow,deny
  Satisfy any
</Location>

<Location /sub/foo>
  Order allow,deny
</Location>

<Location /sub >
  Order deny,allow
  Require valid-user
  Satisfy all
</Location>

<Location /doesnt/match >
  ProxyPass !
</Location>

มันจะสะสมคำสั่งต่อไปนี้ ....

  ProxyPass http://backend.com/
  Order allow,deny
  Satisfy any
  Order allow,deny
  Order deny,allow
  Require valid-user
  Satisfy all   

ด้วยการจับคู่ในภายหลังกำจัดรายการที่ซ้ำกันก่อนหน้าผลใน;

  ProxyPass http://backend.com/
  Order deny,allow
  Require valid-user
  Satisfy all   

คำอธิบายใน
ภายหลังตรงกับการเขียนทับก่อนหน้านี้ตรงกับข้อยกเว้นของ<Directory>ที่ตรงกับการประมวลผลในการสั่งซื้อ: องค์ประกอบไดเรกทอรีที่สั้นที่สุดที่ยาวที่สุด

ตัวอย่างเช่น
<Directory /var/web/dir>
จะถูกประมวลผลก่อน
<Directory /var/web/dir/subdir>
โดยไม่คำนึงถึงลำดับคำสั่งเหล่านั้นที่ระบุในการกำหนดค่าและการจับคู่ที่เฉพาะเจาะจงมากขึ้นชนะ

Locationคำสั่งที่ตรงกันใด ๆจะแทนที่Directoryคำสั่งที่ตรงกันก่อนหน้านี้เสมอ

แนวคิดพื้นฐานคือว่าสำหรับการร้องขอเช่นGET /some/http/request.htmlภายในก็จะได้รับการแปลไปยังสถานที่ในระบบแฟ้มผ่านทางAlias, ScriptAliasหรือสำหรับตำแหน่งแฟ้มปกติภายใต้DocumentRootสำหรับ VirtualHost ว่ามันจับคู่

ดังนั้นคำขอจะมีคุณสมบัติดังต่อไปนี้ซึ่งจะใช้สำหรับการจับคู่:
Location: /some/http/request.html File: /var/www/html/mysite/some/http/request.html Directory: /var/www/html/mysite/some/http

อาปาเช่แล้วจะนำไปใช้ในการเปิดทั้งหมดของDirectoryการแข่งขันเพื่อความจำเพาะไดเรกทอรีจากการตั้งค่าและจากนั้นในการเปิดใช้DirectoryMatch, Filesและในที่สุดก็Locationตรงกับเพื่อที่พวกเขาจะพบ

ดังนั้นการLocationแทนที่Filesซึ่งจะแทนที่DirectoryMatchด้วยการจับคู่พา ธDirectoryที่ระดับความสำคัญต่ำสุด ดังนั้นในตัวอย่างของคุณข้างต้นคำขอให้/sub/foobarจับคู่ตำแหน่ง 3 แห่งแรกตามลำดับดังนั้นตำแหน่งสุดท้ายจึงชนะสำหรับคำสั่งที่ขัดแย้งกัน

(คุณถูกต้องที่ยังไม่ชัดเจนจากเอกสารว่ามีการแก้ไขกรณีขอบบางอย่างอย่างไรอาจเป็นไปได้ว่าallow from *คำสั่งประเภทใดก็ตามจะเชื่อมต่อกับที่เกี่ยวข้องOrder allow,denyแต่ฉันไม่ได้ทดสอบสิ่งนั้นเกิดอะไรขึ้นถ้าคุณจับคู่Satisfy Anyแต่คุณ ได้รวบรวมก่อนหน้านี้Allow from *... )

หมายเหตุที่น่าสนใจเกี่ยวกับ ProxyPass และ Alias

แค่น่ารำคาญProxyPassและAliasดูเหมือนจะทำงานในทิศทางอื่น .... ;-) โดยทั่วไปแล้วมันจะเข้าคู่แรกแล้วหยุดและใช้มัน!

Ordering ProxyPass Directives

The configured ProxyPass and ProxyPassMatch rules are 
checked in the order of configuration. 
The first rule that matches wins. So
usually you should sort conflicting ProxyPass rules starting with the
longest URLs first. Otherwise later rules for longer URLS will be
hidden by any earlier rule which uses a leading substring of the URL.
Note that there is some relation with worker sharing.

For the same reasons exclusions must come before the general 
ProxyPass directives.

ดังนั้นโดยพื้นฐานแล้วนามแฝงและคำสั่ง ProxyPass จะต้องระบุเฉพาะส่วนใหญ่ก่อน

Alias "/foo/bar" "/srv/www/uncommon/bar"
Alias "/foo"     "/srv/www/common/foo"

และ

ProxyPass "/special-area" "http://special.example.com" smax=5 max=10
ProxyPass "/" "balancer://mycluster/" stickysession=JSESSIONID|jsessionid nofailover=On

อย่างไรก็ตามในขณะที่ @orev ได้ชี้ให้เห็น คุณสามารถมีคำสั่ง ProxyPass ในตำแหน่งคำสั่งและดังนั้น ProxyPass ที่เฉพาะเจาะจงมากขึ้นในตำแหน่งจะเอาชนะ ProxyPass ที่พบก่อนหน้านี้


3
ขอบคุณสำหรับการตั้งค่าสถานะคำเตือนเกี่ยวกับการสั่งซื้อ ProxyPass Directives ช่วยให้ฉันปวดหัวอย่างมาก
Jeremy French

2
เกี่ยวกับProxyPass "การทำงานในทิศทางอื่น ๆ"<Location>นี้เป็นจริงเท่านั้นหากพวกเขากำลังนอกของ ใน<Location>กฏ<Location>นั้นมีการปฏิบัติตามกฎการรวมซึ่งหมายความว่าคุณต้องการให้<Location>คำสั่งที่เฉพาะเจาะจงน้อยที่สุดของคุณมาต่อหน้ากฎเกณฑ์ที่เฉพาะเจาะจงมากขึ้น สิ่งนี้อนุญาตให้เฉพาะเจาะจงมากกว่าแทนที่คำสั่งที่เฉพาะเจาะจงน้อยลง คุณสามารถมีได้เพียงหนึ่งต่อProxyPass <Location>
orev
โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.