การจับคู่ URL ที่สั้นที่สุดใน JavaScript


16

สร้างนิพจน์ปกติที่สั้นที่สุดซึ่งจะจับคู่กับ URL ในข้อความเมื่อเรียกใช้ใน JavaScript

ตัวอย่าง:

"some text exampley.com".match(/your regular expression goes here/);

การแสดงออกปกติต้อง

  • รวบรวม URL ที่ถูกต้องทั้งหมดที่ใช้สำหรับ http และ https
  • ไม่ต้องกังวลกับการไม่จับคู่สำหรับสตริงการค้นหา URL ที่ไม่ถูกต้องเช่น URL super.awesome/cool
  • จะถูกต้องเมื่อเรียกใช้เป็น JavaScript regex

เกณฑ์การทดสอบ:

การจับคู่:

ไม่ตรงกับ:

  • ตัวอย่าง
  • ซุปเปอร์ / เย็น
  • อรุณสวัสดิ์
  • ฉันสามารถ
  • สวัสดี.

นี่คือการทดสอบที่อาจช่วยชี้แจงเล็กน้อยhttp://jsfiddle.net/MikeGrace/gsJyr/

ฉันขอโทษสำหรับการขาดความชัดเจนฉันไม่ได้ตระหนักถึงวิธีการที่ตรงกับ URL ที่น่ากลัว


Ahgrrrr! ฉันคิดถึงสิทธิ์แก้ไขของฉัน! ฉันจะ จำกัด เกมเป็นหนึ่งภาษาบางทีคุณควรติดแท็กด้วยภาษานั้น
dmckee --- ผู้ดูแลอดีตลูกแมว

ประกอบด้วยอักขระ URL ที่ถูกต้องคืออะไร เพราะฉันสามารถใช้\wกับทุกสิ่งคุณคาดหวังว่าจะมีการอ้างอิงย้อนกลับสำหรับส่วนประกอบ URL ที่แตกต่างกันหรือไม่?
Ming-Tang

1
"เป็น URI เป็นลำดับของตัวละครจากชุดที่ จำกัด มากเช่นตัวอักษรของตัวอักษรละตินพื้นฐาน, ตัวเลขและตัวอักษรพิเศษไม่กี่" ตามRFC 2396
RunnerRick

Mike: ฉันคิดว่ายังคงมีคำชี้แจงอยู่บ้าง ในขณะนี้ฉันสามารถใช้/:/เป็นนิพจน์ปกติและจับคู่ URI ที่ถูกต้องได้และไม่ตรงกับตัวอย่างทั้งหมดของคุณในรายการ»ไม่ตรงกัน« ตราบใดที่คุณกำลังไปเส้นทางนั้นมันเป็นคำถาม: อะไรคือนิพจน์ปกติที่สั้นที่สุดที่จะไม่ตรงกับตัวอย่างใด ๆ ของสตริง แต่ยังคงจับ URIs ทั้งหมด
Joey

1
เพียงลองเขียนความท้าทายที่ยาวขึ้นพร้อมรายละเอียดเพิ่มเติม

คำตอบ:


1
/.+\.\w\w.*/

ไม่ตรงกับ 3 สายที่ไม่ควรตรงกับเกือบทุกอย่างอื่น)
อัพเดท:มันยังไม่ตรงกับ 5 ทั้งหมด


14

อันนี้ใช้ได้ผล:

var re = /(^|\s)((https?:\/\/)?[\w-]+(\.[\w-]+)+\.?(:\d+)?(\/\S*)?)/gi;

/*
(^|\s)                            : ensure that we are not matching an url 
                                    embeded in an other string
(https?:\/\/)?                    : the http or https schemes (optional)
[\w-]+(\.[\w-]+)+\.?              : domain name with at least two components;
                                    allows a trailing dot
(:\d+)?                           : the port (optional)
(\/\S*)?                          : the path (optional)
*/

ผ่านการทดสอบที่http://jsfiddle.net/9BYdp/1/

ยังตรงกับ:

  • example.com (จุดต่อท้าย)
  • example.com:8080 (พอร์ต)

หวาน !!!!!!!
Mike Grace

2
คุณไม่ต้องการจับคู่ชื่อโฮสต์กับส่วนประกอบเดียวเช่นกัน (localhost) ใช่ไหม
RunnerRick

สิ่งนี้อนุญาตให้มีช่องว่าง
brenjt

ทำงานได้สำหรับฉัน ty :)
STEEL

ใช้งานได้ดี แต่ไม่ใช่สำหรับโดเมนที่มีส่วนของผู้ใช้ / รหัสผ่านเช่นhttp://user:password@domain.com/path
Radon8472

5

เห็นได้ชัดว่าสิ่งนี้ไม่ได้ทำในสิ่งที่คุณตั้งใจ แต่มันตรงตามเกณฑ์ของคุณ:

 /.*/
  • "จับคู่ URL ที่ถูกต้องทั้งหมดที่ใช้สำหรับ http และ https"

    ใช่แน่นอนจะจับคู่

  • "ไม่ต้องกังวลว่าจะไม่จับคู่กับสตริงการค้นหา URL ที่ไม่ถูกต้องจริง ๆ เช่น 'super.awesome / cool' URL

    ใช่แน่นอนจะมีผลบวกปลอมจำนวนมากแต่คุณพูดว่าไม่สำคัญ

  • จะถูกต้องเมื่อเรียกใช้เป็น JavaScript regex

    แน่นอนว่าไข่ทำงานได้ตามที่คุณพูด

หากผลลัพธ์นี้ไม่ใช่คำตอบที่ถูกต้องคุณจะต้องเลือกเกณฑ์ของคุณให้มากขึ้น

เพื่อให้เป็นกฎที่ใช้งานได้ตามที่คุณตั้งใจจริง ๆ แล้วคุณทำจำเป็นที่จะต้องดำเนินการ RFC เต็มรูปแบบการจับคู่ที่สอดคล้องและ RFC เต็มรูปแบบที่สอดคล้องกับการจับคู่จะ "ไม่ต้องกังวลเกี่ยวกับการไม่ตรงกับ"

ดังนั้นในแง่ของ "การอนุญาตไม่จับคู่" คุณต้องระบุอย่างชัดเจนเบี่ยงเบนจาก RFC ใดที่ได้รับอนุญาต

สิ่งอื่นใดและการออกกำลังกายทั้งหมดนี้เป็นการหลอกลวงเพราะผู้คนจะเขียนสิ่งใดก็ตามที่เหมาะกับพวกเขาหรือว่าพวกเขาชอบมันอย่างไรและเสียสละ "ทำความเข้าใจใด ๆ " ในความโปรดปรานที่จะสั้น (เหมือนฉัน)

ในการอัพเดทของคุณ

Regex ที่ไร้เดียงสาที่สุดที่ฉันสามารถหาได้ด้วยการจับคู่ (และจับ) ตัวอย่างที่คุณวางไว้ทั้งหมดคือ:

/(\S+\.[^/\s]+(\/\S+|\/|))/g;

มันค่อนข้างง่ายในธรรมชาติและถือว่ามีเพียง 3 รูปแบบพื้นฐานเท่านั้น

x.y
x.y/
x.y/z 

zสามารถ anthing ไม่ช่องว่าง xสามารถเป็นอะไรก็ได้ที่ไม่ใช่ช่องว่าง yสามารถเป็นอะไรก็ได้ที่ไม่ใช่ช่องว่างหรืออักขระ '/'

มีหลายสิ่งหลายอย่างที่จะใช้ได้กับกฎนี้มากมาย แต่อย่างน้อยพวกเขาจะดูเหมือน URI ที่ถูกต้องกับมนุษย์พวกเขาเพียง แต่จะไม่เข้ากันได้กับข้อกำหนด

เช่น:

hello.0/1  # valid 
1.2/1 # valid 
muffins://¥.µ/€  # probably valid

ฉันคิดว่าวิธีที่มีสติคือการแยกสิ่งที่น่าจะเป็นของ URI จากนั้นตรวจสอบพวกเขาด้วยสิ่งที่เข้มงวดกว่าฉันกำลังมองหาวิธีการใช้เบราว์เซอร์ URI class เพื่อตรวจสอบพวกเขา =)

แต่คุณสามารถเห็นเหตุผลข้างต้นทำงานกับตัวอย่างนี้ได้ที่นี่: http://jsfiddle.net/mHbXx/


เขาเปลี่ยนคำถาม แต่คุณสามารถทำได้ดีกว่าด้วย/:/ซ้ำหลังจากแก้ไข :-)
Joey

ขอบคุณไมค์ =) ฉันไม่ต้องการที่จะแข่งขันด้วยตนเองอย่างจริงจังยิ่งขึ้นข้อเสนอแนะอื่น ๆ นั้นมีประโยชน์มากกว่าฉันแค่อยากจะชี้ให้เห็นปัญหาของการเริ่มต้นเพื่อที่คุณภาพของคำถามจะดีขึ้น =)
Kent Fredric

เป็นเพียงฉันหรือเป็น "www .google .com" ที่ตรงกันหรือไม่
Schiavini

1
/https?\:\/\/\w+((\:\d+)?\/\S*)?/

ลองดู

ฉันรวมเครื่องหมายทับที่นำหน้าและต่อท้ายที่กั้นการแสดงออกปกติดังนั้นหวังว่าจะไม่ทำให้ตัวละครของฉันเสียหาย!

รูปแบบนี้ จำกัด โปรโตคอลไว้ที่ http หรือ https อนุญาตให้ใช้หมายเลขพอร์ตที่เป็นทางเลือกจากนั้นอนุญาตให้ใช้อักขระใดก็ได้ยกเว้นช่องว่าง

โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.