คุณจำโปรแกรมแรกที่คุณเคยเขียนได้ไหม? ผมจำของผมได้ มันเป็นโปรแกรมกราฟิกเล็ก ๆ ที่ผมเขียนบน PC รุ่นแรก ๆ ผมเริ่มเขียนโปรแกรมช้ากว่าเพื่อนส่วนใหญ่ของผม แน่นอนว่าผมเคยเห็นคอมพิวเตอร์ตอนเป็นเด็ก ผมจำได้ว่าประทับใจ minicomputer เครื่องหนึ่งที่เคยเห็นในออฟฟิศ แต่หลายปีผ่านไปผมก็ไม่มีโอกาสได้นั่งหน้า computer เลย ต่อมาเมื่อเป็นวัยรุ่น เพื่อนบางคนของผมซื้อ TRS-80 เครื่องแรก ๆ ผมก็สนใจ แต่จริง ๆ แล้วก็รู้สึกเกร็ง ๆ เหมือนกัน ผมรู้ว่าถ้าเริ่มเล่น computer แล้วหละก็ ผมจะถูกดูดเข้าไป มันดูเจ๋งเกินไป ผมไม่รู้ว่าทำไมถึงรู้จักตัวเองดีขนาดนั้น แต่ก็ยั้งไว้ได้ ต่อมาในมหาวิทยาลัย เพื่อนร่วมห้อง คนหนึ่งมี computer และผมซื้อ C compiler เพื่อจะสอนตัวเองเขียนโปรแกรม แล้วมันก็เริ่มขึ้น ผมนอนดึก แล้วดึกอีกเพื่อลองอะไรต่ออะไร อ่าน source code ของ emacs editor ที่มากับ compiler มันเสพติด มันท้าทาย และผมรักมัน

ผมหวังว่าคุณจะเคยมีประสบการณ์แบบนี้—ความสุขดิบ ๆ ของการทำให้สิ่งต่าง ๆ ทำงานบน computer นักพัฒนาเกือบทุกคน ที่ผมถามก็เคยมี ความสุขนั้นเป็นส่วนหนึ่งที่ทำให้เราเข้ามาทำงานสายนี้ แต่มันหายไปไหนในชีวิตประจำวัน?

สองสามปีก่อน ผมโทรหาเพื่อนของผม Erik Meade หลังจากเลิกงานค่ำวันหนึ่ง ผมรู้ว่า Erik เพิ่ง เริ่มงานรับเหมากับทีมใหม่ ผมเลยถามว่า "พวกเขาเป็นยังไงบ้าง?" เขาตอบว่า "พวกเขากำลังเขียน legacy code อยู่ไงพวก" นั่นเป็นหนึ่งในครั้งไม่กี่ครั้งในชีวิตที่ผมรู้สึกถูกต่อยด้วยคำพูดของเพื่อนร่วมงาน ผมรู้สึกถึงมัน ในท้องเลยทีเดียว Erik ได้เอ่ยคำพูดถึงความรู้สึกที่ผมมักจะเจอตอนไปเยี่ยมทีมต่าง ๆ เป็นครั้งแรก พวกเขา พยายามอย่างหนัก แต่สุดท้ายแล้วด้วยแรงกดดันเรื่องเวลา น้ำหนักของประวัติศาสตร์ หรือการไม่มี code ที่ดีกว่านี้มาเปรียบเทียบ หลายคนกำลังเขียน legacy code อยู่

แล้ว legacy code คืออะไร? ผมใช้คำนี้โดยไม่นิยามมัน มาดูนิยามแบบตรงตัวกัน: Legacy code คือ code ที่เราได้รับมาจากคนอื่น บริษัทของเราอาจซื้อ code จากอีกบริษัทหนึ่ง หรือคนในทีมเดิม ย้ายไปโปรเจกต์อื่นแล้ว Legacy code คือ code ของคนอื่น แต่ในภาษาโปรแกรมเมอร์ คำนี้มีความหมาย มากกว่านั้นมาก คำว่า legacy code ได้รับความหมายและน้ำหนักที่เพิ่มมากขึ้นเรื่อย ๆ เมื่อเวลาผ่านไป

คุณคิดถึงอะไรเมื่อได้ยินคำว่า legacy code ? ถ้าคุณเหมือนผมสักนิด คุณคงนึกถึงโครงสร้างที่พันกันยุ่งเหยิง เข้าใจยาก code ที่คุณต้องเปลี่ยนแต่ไม่ เข้าใจจริง ๆ คุณนึกถึงคืนนอนไม่หลับที่พยายามเพิ่ม feature ที่ควรจะเพิ่มได้ง่าย และคุณนึกถึง ความท้อแท้ ความรู้สึกที่ว่าทุกคนในทีมเบื่อหน่าย code base จนดูเหมือนเกินเยียวยา เป็น code แบบที่คุณหวังให้มันตายไปซะ ส่วนหนึ่งของคุณรู้สึกแย่ด้วยซ้ำที่คิดจะทำให้มันดีขึ้น มันดู ไม่คู่ควรกับความพยายามของคุณ นิยามของ legacy code แบบนั้นไม่เกี่ยวกับว่าใครเป็นคนเขียน code Code สามารถเสื่อมถอยได้หลายทาง และหลายทางนั้นไม่เกี่ยวข้องกับว่า code มาจากทีมอื่นหรือไม่

ในวงการ legacy code มักถูกใช้เป็นคำสแลงสำหรับ code ที่เปลี่ยนแปลงยากและเราไม่เข้าใจ แต่ตลอดหลายปีที่ทำงาน ร่วมกับทีมต่าง ๆ ช่วยให้พวกเขาผ่านปัญหาหนัก ๆ ด้าน code ผมก็ได้ข้อสรุปที่แตกต่างออกไป

สำหรับผม legacy code ก็แค่ code ที่ไม่มี tests ผมโดนตำหนิมาบ้างสำหรับนิยามนี้ แล้ว tests ไปเกี่ยวข้องอะไรกับ ว่า code ดีหรือไม่ดี? สำหรับผม คำตอบตรงไปตรงมา และเป็นประเด็นที่ผมจะอธิบายตลอดทั้งเล่ม:


Code ที่ไม่มี tests คือ code ที่แย่ ไม่สำคัญว่าจะเขียนดีแค่ไหน ไม่สำคัญว่าจะสวยหรูหรือเป็น object-oriented หรือมีการ encapsulate ดีแค่ไหนเพียงใด เมื่อมี tests เราสามารถเปลี่ยนพฤติกรรมของ code ได้อย่างรวดเร็วและตรวจสอบได้ หากไม่มี tests เราก็ไม่รู้จริง ๆ ว่า code กำลังดีขึ้นหรือแย่ลง


คุณอาจคิดว่านี่รุนแรงเกินไป แล้ว code ที่สะอาดหละ? ถ้า code base สะอาดและมีโครงสร้างดีมาก มันยังไม่พอหรือ? อย่าเข้าใจผิดนะครับ ผมรัก code ที่สะอาด ผมรักมันมากกว่าคนส่วนใหญ่ที่ผมรู้จัก แต่ถึง code ที่สะอาดจะดี แต่มันก็ยังไม่พอ ทีมต้องเสี่ยงมากเมื่อพยายามเปลี่ยนแปลงครั้งใหญ่โดยไม่มี tests มันเหมือนการเล่นยิมนาสติกกลางอากาศโดยไม่มีตาข่ายรองรับ มันต้องใช้ทักษะที่เหลือเชื่อและความเข้าใจที่ชัดเจน ว่าเกิดอะไรขึ้นได้ในทุกย่างก้าว การรู้ว่าจะเกิดอะไรขึ้นถ้าคุณเปลี่ยนตัวแปรสองสามตัวนั้น มักจะเหมือนกับการรู้ว่านักยิมนาสติกอีกคนจะรับข้อมือคุณได้หรือไม่หลังจากที่คุณตีลังกา ถ้าคุณอยู่ในทีมที่มี code ชัดเจนขนาดนั้น คุณก็อยู่ในตำแหน่งที่ดีกว่าโปรแกรมเมอร์ส่วนใหญ่ ในงานของผม ผมสังเกตว่าทีมที่มีความชัดเจนในระดับนั้นใน code ทั้งหมดของพวกเขานั้นหายาก พวกเขาดูเหมือนความผิดปกติทางสถิติ และคุณรู้ไหม ถ้าพวกเขาไม่มี tests ที่สนับสนุน การเปลี่ยนแปลง code ของพวกเขาก็ยังดูช้ากว่าทีมที่มี tests

ใช่ ทีมพัฒนาได้ดีขึ้นและเริ่มเขียน code ที่ชัดเจนขึ้น แต่มันต้องใช้เวลานานสำหรับ code เก่า ที่จะชัดเจนขึ้น ในหลายกรณี มันจะไม่มีทางเกิดขึ้นอย่างสมบูรณ์ ด้วยเหตุนี้ ผมจึงไม่มีปัญหาในการนิยาม legacy code ว่าเป็น code ที่ไม่มี tests มันเป็นนิยามที่ใช้การได้ดี และมันชี้ไปทางออก

ผมพูดถึง tests มาพอสมควรแล้ว แต่หนังสือเล่มนี้ไม่ได้เกี่ยวกับการ testing หนังสือเล่มนี้เกี่ยวกับการสามารถเปลี่ยนแปลง code base ใด ๆ ได้อย่างมั่นใจ ในบทต่อ ๆ ไป ผมจะอธิบายเทคนิคที่คุณสามารถใช้เพื่อทำความเข้าใจ code ทำให้มันอยู่ภายใต้ test, refactor และเพิ่ม features

สิ่งหนึ่งที่คุณจะสังเกตเมื่ออ่านหนังสือเล่มนี้คือ มันไม่ใช่หนังสือเกี่ยวกับ code ที่สวยงาม ตัวอย่างที่ผมใช้ในหนังสือเป็นตัวอย่างที่สร้างขึ้นเพราะผมทำงานภายใต้ข้อตกลงไม่เปิดเผยข้อมูลกับลูกค้า แต่ในหลายตัวอย่าง ผมพยายามคงจิตวิญญาณของ code ที่ผมเห็นในภาคสนามไว้ ผมจะไม่บอกว่าตัวอย่างเหล่านั้นเป็นตัวแทนเสมอไป แน่นอนว่ามีโอเอซิสของ code ที่ยอดเยี่ยมอยู่ทั่วไป แต่พูดตามตรง ก็มี code ที่แย่กว่าสิ่งที่ผมใช้เป็นตัวอย่างในหนังสือเล่มนี้มากมายอีก นอกเหนือจากการรักษาความลับของลูกค้าแล้ว ผมก็ไม่สามารถใส่ code แบบนั้นในหนังสือเล่มนี้ โดยไม่ทำให้คุณเบื่อจนหลับและกลบประเด็นสำคัญในรายละเอียดที่รกรุงรัง ส่งผลให้หลายตัวอย่างค่อนข้างสั้น ถ้าคุณดูตัวอย่างใดตัวอย่างหนึ่งแล้วคิดว่า "ไม่ เขาไม่เข้าใจ— methods ของฉันใหญ่กว่านั้นมากและแย่กว่ามาก" ก็ขอให้ดูคำแนะนำที่ผมให้ตามที่มันเป็น และดูว่ามันใช้ได้หรือไม่ แม้ว่าตัวอย่างจะดูง่ายกว่า

เทคนิคต่าง ๆ ในที่นี้ได้ถูกทดสอบกับ code ขนาดใหญ่อย่างมีนัยสำคัญจริง ๆ มันเป็นเพียงข้อจำกัดของรูปแบบหนังสือที่ทำให้ตัวอย่างเล็กลง โดยเฉพาะอย่างยิ่ง เมื่อคุณเห็นจุดไข่ปลา (...) ใน code fragment แบบนี้ คุณสามารถอ่านมันเป็น "ใส่ code ขยะ 500 บรรทัดตรงนี้":

m_pDispatcher->register(listener);
...
m_nMargins++;

ถ้าหนังสือเล่มนี้ไม่เกี่ยวกับ code ที่สวยงาม มันก็ยิ่งไม่เกี่ยวกับ design ที่สวยงามอีก การออกแบบที่ดีควรเป็นเป้าหมายของเราทุกคน แต่ใน legacy code มันคือสิ่งที่เราค่อย ๆ ไปถึง ในบางบท ผม describe วิธีการเพิ่ม code ใหม่เข้าไปใน code base ที่มีอยู่ และแสดงวิธีเพิ่มมันด้วยหลักการออกแบบที่ดี คุณสามารถเริ่มปลูกฝังพื้นที่ของ code ที่มีคุณภาพสูงมากใน legacy code bases ได้ แต่อย่าแปลกใจถ้าบางขั้นตอนที่คุณทำ เพื่อเปลี่ยนแปลงจะทำให้ code ดูแย่ลงเล็กน้อย งานนี้เหมือนการผ่าตัด เราต้องกรีด และต้องเคลื่อนผ่านไส้ในและระงับการตัดสินเรื่องความสวยงามไว้ก่อน อวัยวะสำคัญและเครื่องในของผู้ป่วยคนนี้ดีกว่านี้ได้ไหม? ได้ แล้วเราจะแค่ลืมปัญหาปัจจุบันของเขา เย็บเขากลับเข้าไป แล้วบอกให้เขากินอาหารที่มีประโยชน์และฝึกซ้อมวิ่งมาราธอน? เราทำแบบนั้นได้ แต่สิ่งที่เราต้องทำจริง ๆ คือรับผู้ป่วยอย่างที่เขาเป็น แก้ไขสิ่งที่ผิด และพาเขาไปสู่สภาวะที่แข็งแรงขึ้น เขาอาจจะไม่มีวันเป็นนักกีฬาโอลิมปิก แต่เราไม่สามารถปล่อยให้ "ดีที่สุด" เป็นศัตรูกับ "ดีขึ้น" Code bases สามารถแข็งแรงขึ้นและทำงานง่ายขึ้น เมื่อผู้ป่วยรู้สึกดีขึ้นเล็กน้อย นั่นคือเวลาที่คุณสามารถช่วยให้เขามุ่งมั่นที่จะใช้ชีวิตที่มีสุขภาพดีขึ้น นั่นคือสิ่งที่เราพยายามทำให้สำเร็จกับ legacy code เรากำลังพยายามไปถึงจุดที่เราคุ้นเคยกับความสะดวก เราคาดหวังมันและพยายามอย่างแข็งขันที่จะทำให้การเปลี่ยน code ง่ายขึ้น เมื่อเราสามารถรักษาความรู้สึกนั้นไว้ในทีมได้ design ก็จะดีขึ้น

เทคนิคที่ผม describe เป็นเทคนิคที่ผมค้นพบและเรียนรู้ร่วมกับเพื่อนร่วมงานและลูกค้า ตลอดหลายปีที่ทำงานกับลูกค้าเพื่อพยายามสร้างการควบคุมเหนือ code bases ที่ไร้ระเบียบ ผมเข้ามาสู่จุดเน้นเรื่อง legacy code นี้โดยบังเอิญ ตอนที่ผมเริ่มทำงานกับ Object Mentor งานส่วนใหญ่ของผมคือการช่วยเหลือทีมที่มีปัญหาหนัก ๆ ในการพัฒนาทักษะและการปฏิสัมพันธ์ จนถึงจุดที่พวกเขาสามารถส่งมอบ code ที่มีคุณภาพได้อย่างสม่ำเสมอ เรามักใช้ Extreme Programming practices เพื่อช่วยให้ทีมควบคุมงานของพวกเขา ทำงานร่วมกันอย่างเข้มข้น และส่งมอบ ผมมักรู้สึกว่า Extreme Programming เป็นวิธีการพัฒนาซอฟต์แวร์น้อยกว่าที่มันเป็นวิธีการสร้างทีมงานที่เข้ากันได้ดี ซึ่งบังเอิญส่งมอบซอฟต์แวร์ที่ยอดเยี่ยมทุกสองสัปดาห์

แต่ตั้งแต่แรกเริ่มก็มีปัญหาอยู่ โปรเจกต์ XP แรก ๆ หลายโปรเจกต์เป็นโปรเจกต์ "greenfield" ลูกค้าที่ผมพบเจอมี code bases ที่ใหญ่มาก และพวกเขากำลังมีปัญหา พวกเขาต้องการวิธีในการควบคุมงานของพวกเขาและเริ่มส่งมอบ เมื่อเวลาผ่านไป ผมพบว่าผมทำสิ่งเดิมซ้ำแล้วซ้ำเล่ากับลูกค้า ความรู้สึกนี้ถึงจุดสูงสุดในงานที่ผมทำกับทีมในอุตสาหกรรมการเงิน ก่อนที่ผมจะมาถึง พวกเขาตระหนักแล้วว่า unit testing เป็นสิ่งที่ดี แต่ tests ที่พวกเขาเรียกใช้เป็น full scenario tests ที่เรียก database หลายครั้ง และรัน code จำนวนมาก Tests เขียนยาก และทีมไม่ได้รันมันบ่อยนักเพราะใช้เวลานาน ตอนที่ผมนั่งลงกับพวกเขาเพื่อ break dependencies และทำให้ code ชิ้นเล็กลงมาอยู่ภายใต้ test ผมมีความรู้สึก déjà vu อย่างรุนแรง ดูเหมือนว่าผมกำลังทำงานแบบนี้กับทุกทีมที่เจอ และมันเป็นสิ่งที่ไม่มีใครอยากจะคิดถึง มันเป็นแค่งานสกปรกที่คุณทำ เมื่อคุณต้องการเริ่มทำงานกับ code ของคุณอย่างควบคุมได้ ถ้าคุณรู้วิธีทำ ผมตัดสินใจตอนนั้นว่ามันคุ้มค่าที่จะสะท้อนว่าเราแก้ปัญหาเหล่านี้อย่างไร และเขียนมันลงไปเพื่อให้ทีมต่าง ๆ สามารถตั้งหลักและทำให้ code bases ของพวกเขา อยู่ง่ายขึ้น

หมายเหตุเกี่ยวกับตัวอย่าง: ผมใช้ตัวอย่างในภาษาการเขียนโปรแกรมหลายภาษา ตัวอย่างส่วนใหญ่เขียนด้วย Java, C++ และ C ผมเลือก Java เพราะเป็นภาษาที่ใช้กันทั่วไป และผมรวม C++ เพราะมันมีความท้าทายพิเศษในสภาพแวดล้อมของ legacy code ผมเลือก C เพราะมันชี้ให้เห็นปัญหามากมายที่เกิดขึ้นใน procedural legacy code ในบรรดาภาษาเหล่านี้ พวกมันครอบคลุมสเปกตรัมของความกังวลที่เกิดขึ้นใน legacy code อย่างไรก็ตาม ถ้าภาษาที่คุณใช้ไม่ได้อยู่ในตัวอย่าง ก็ลองดูตัวอย่างเหล่านั้นนะ เทคนิคหลายอย่างที่ผมครอบคลุมสามารถใช้ได้กับภาษาอื่น เช่น Delphi, Visual Basic, COBOL และ FORTRAN

ผมหวังว่าคุณจะพบว่าเทคนิคต่าง ๆ ในหนังสือเล่มนี้มีประโยชน์ และมันจะช่วยให้คุณ กลับไปสู่สิ่งที่จะทำให้การเขียนโปรแกรมสนุกอีกครั้ง การเขียนโปรแกรมสามารถเป็นงานที่ ให้รางวัลและมีความสุขมาก ถ้าคุณไม่รู้สึกแบบนั้นในงานประจำวันของคุณ ผมหวังว่าเทคนิคที่ผมนำเสนอในหนังสือเล่มนี้จะช่วยให้คุณค้นพบมัน และขยายมันในทีมของคุณ

Acknowledgments (กิตติกรรมประกาศ)

ก่อนอื่นเลย ผมเป็นหนี้บุญคุณอย่างใหญ่หลวงต่อ Ann ภรรยาของผม และลูก ๆ ของผม Deborah และ Ryan ความรักและการสนับสนุนของพวกเขาทำให้หนังสือเล่มนี้และการเรียนรู้ทั้งหมดที่นำมาก่อนหน้านี้เป็นไปได้ ผมขอขอบคุณ "Uncle Bob" Martin ประธานและผู้ก่อตั้ง Object Mentor แนวทางเชิงปฏิบัติที่เคร่งครัดของเขาในการพัฒนาและการออกแบบ การแยกสิ่งที่สำคัญออกจากสิ่งที่ไม่สำคัญ ทำให้ผมมีสิ่งยึดเหนี่ยวเมื่อประมาณ 10 ปีที่แล้ว ตอนที่ผมดูเหมือนจะจมดิ่งอยู่ในคลื่นของคำแนะนำที่ไม่สมจริง และขอบคุณ Bob ที่ให้โอกาสผมได้เห็น code และทำงานกับผู้คนมากมายในช่วงห้าปีที่ผ่านมา มากกว่าที่ผมเคยจินตนาการไว้

ผมต้องขอขอบคุณ Kent Beck, Martin Fowler, Ron Jeffries และ Ward Cunningham ที่ให้คำแนะนำแก่ผมในหลาย ๆ โอกาส และสอนผมมากมายเกี่ยวกับการทำงานเป็นทีม การออกแบบ และการเขียนโปรแกรม ขอบคุณเป็นพิเศษสำหรับทุกคนที่ reviewed ต้นฉบับ ผู้ review อย่างเป็นทางการคือ Sven Gorts, Robert C. Martin, Erik Meade และ Bill Wake ส่วนผู้ review อย่างไม่เป็นทางการคือ Dr. Robert Koss, James Grenning, Lowell Lindstrom, Micah Martin, Russ Rufer และ Silicon Valley Patterns Group และ James Newkirk

ขอบคุณเช่นกันสำหรับผู้ review ต้นฉบับช่วงแรก ๆ ที่ผมวางบนอินเทอร์เน็ต feedback ของพวกเขามีผลอย่างมากต่อทิศทางของหนังสือหลังจากที่ผมจัดรูปแบบใหม่ ผมขออภัยล่วงหน้าถ้าเผลอลืมใครไป ผู้ review ช่วงแรก ๆ ได้แก่: Darren Hobbs, Martin Lippert, Keith Nicholas, Phlip Plumlee, C. Keith Ray, Robert Blum, Bill Burris, William Caputo, Brian Marick, Steve Freeman, David Putman, Emily Bache, Dave Astels, Russel Hill, Christian Sepulveda และ Brian Christopher Robinson

ขอบคุณ Joshua Kerievsky ที่ให้ review ช่วงแรก ๆ ที่สำคัญ และ Jeff Langr ที่ช่วยด้วยคำแนะนำและ spot reviews ตลอดทั้งกระบวนการ

ผู้ review ช่วยให้ผมขัดเกลาต้นฉบับได้อย่างมาก แต่ถ้ามีข้อผิดพลาดหลงเหลืออยู่ มันเป็นของผมทั้งหมด

ขอบคุณ Martin Fowler, Ralph Johnson, Bill Opdyke, Don Roberts และ John Brant สำหรับงานของพวกเขาในด้าน refactoring มันเป็นแรงบันดาลใจ

ผมเป็นหนี้บุญคุณพิเศษต่อ Jay Packlick, Jacques Morel และ Kelly Mower แห่ง Sabre Holdings และ Graham Wright แห่ง Workshare Technology สำหรับการสนับสนุนและ feedback ของพวกเขา

ขอบคุณเป็นพิเศษสำหรับ Paul Petralia, Michelle Vincenti, Lori Lyons, Krista Hansing และทีมงานที่เหลือของ Prentice-Hall ขอบคุณ Paul สำหรับความช่วยเหลือ และกำลังใจทั้งหมดที่นักเขียนครั้งแรกอย่างผมต้องการ

ขอบคุณเป็นพิเศษสำหรับ Gary และ Joan Feathers, April Roberts, Dr. Raimund Ege, David Lopez de Quintana, Carlos Perez, Carlos M. Rodriguez และ Dr. John C. Comfort ผู้ล่วงลับ สำหรับความช่วยเหลือและกำลังใจตลอดหลายปี ผมต้องขอขอบคุณ Brian Button สำหรับตัวอย่างใน Chapter 21 , I'm Changing the Same Code All Over the Place เขาเขียน code นั้นในเวลาประมาณหนึ่งชั่วโมงตอนที่เราพัฒนาหลักสูตร refactoring ด้วยกัน และมันกลายเป็น code การสอนที่ผมชอบมากที่สุด

และขอขอบคุณเป็นพิเศษสำหรับ Janik Top ที่ผลงานเพลง De Futura ของเขาเป็น soundtrack ในช่วงสองสามสัปดาห์สุดท้ายของการทำงานหนังสือเล่มนี้

สุดท้ายนี้ ผมขอขอบคุณทุกคนที่ผมทำงานด้วยตลอดไม่กี่ปีที่ผ่านมา ที่ insights และความท้าทายของพวกเขาได้เสริมเนื้อหาในหนังสือเล่มนี้ให้แข็งแกร่งขึ้น

Michael Feathers
[email protected]
www.objectmentor.com
www.michaelfeathers.com