<?xml version='1.0' encoding='UTF-8'?><?xml-stylesheet href="http://www.blogger.com/styles/atom.css" type="text/css"?><feed xmlns='http://www.w3.org/2005/Atom' xmlns:openSearch='http://a9.com/-/spec/opensearchrss/1.0/' xmlns:georss='http://www.georss.org/georss' xmlns:gd='http://schemas.google.com/g/2005' xmlns:thr='http://purl.org/syndication/thread/1.0'><id>tag:blogger.com,1999:blog-6082242</id><updated>2011-11-25T15:23:13.852Z</updated><category term='ruby'/><category term='vs.net'/><category term='xml'/><category term='idea'/><category term='GLIO'/><category term='Continuous Integration'/><category term='iis'/><category term='photoshop tips'/><category term='photography'/><category term='win server'/><category term='object'/><category term='nant'/><category term='nunit'/><category term='Java'/><category term='SOA'/><category term='Life'/><category term='not work'/><category term='sql'/><category term='configuration'/><category term='web 2.0'/><category term='web service'/><category term='asp.net'/><category term='source control'/><category term='tdd'/><category term='.net'/><category term='mono'/><category term='service component'/><category term='html css'/><title type='text'>JBlogs</title><subtitle type='html'>A .Net Developer's Dumpster</subtitle><link rel='http://schemas.google.com/g/2005#feed' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/posts/default'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default?max-results=100'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/'/><link rel='hub' href='http://pubsubhubbub.appspot.com/'/><link rel='next' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default?start-index=101&amp;max-results=100'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><generator version='7.00' uri='http://www.blogger.com'>Blogger</generator><openSearch:totalResults>140</openSearch:totalResults><openSearch:startIndex>1</openSearch:startIndex><openSearch:itemsPerPage>100</openSearch:itemsPerPage><entry><id>tag:blogger.com,1999:blog-6082242.post-1764301461237588904</id><published>2008-01-26T00:09:00.000Z</published><updated>2008-01-26T00:10:45.254Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='Life'/><category scheme='http://www.blogger.com/atom/ns#' term='not work'/><title type='text'>Almost missed the flight to Hong Kong</title><content type='html'>It was the big day yesterday. The family, Ryan (5 months) Danni my wife and me was on a long haul fight from London to Hong Kong then en-route to China to see the family there. To get to the Gatwick airport, we need to take express train from home station.&lt;br /&gt;&lt;br /&gt;Once a few years back, I have some bad experience on rail travel to this airport. The distance is so long, it involves at least one connection, maybe two or three if need to going to central London first. In that incident, the delayed railway work had many train services cancelled, and we had been delayed at the start of the trip – then a chain of delays had we missed the fight when were finally at the airport although we leave a plenty of time for the travel.&lt;br /&gt;&lt;br /&gt;The Deja Vu was back this time. We almost miss the flight yesterday.&lt;br /&gt;&lt;br /&gt;We arrived at train station at 18 minutes before it arrived. Two huge luggage, three pieces hand carried bags, Ryan and his buggy were unloaded from the taxi. Did I say three? Wait, ‘honey, do you see my laptop bag?’ &lt;br /&gt;&lt;br /&gt;The bag with laptop and other important things was left at home. Without them I have to cut short my hols, and buy another ticket home in two weeks time. Panic, in a very desperate attempt, Danni, Ryan and a suitcase were left at the platform, put one rucksack back, and I was drove home with the taxi to get the bag.&lt;br /&gt;&lt;br /&gt;It 9s about 10-15 minute one way drive from home to the station in a clear traffic. This time it was very busy, the lunch hour. A lorry and a wagon joined up in front, every traffic light turned into red when we up to it. Radio reported midday, 12 minutes before the train arrives on half way to my home.&lt;br /&gt;&lt;br /&gt;I didn't know how Danni would handle things neither: buggy, a huge suitcase (38KG) and Ryan. Some passed-by help her to move the suitcase into the station concourse. But then and she needs to draw some cash from outside station and collect tickets from fast ticket machine. I thought I am going to miss them.&lt;br /&gt;&lt;br /&gt;Taxi pulled stop at a near exit it may make it a minute or two quicker than if drove up. I ran the shortcut uphill to collect the bag, locked the door. The heart was beating so fast, and the hand is so shaky I dropped the key when locking the door. Ran the short cut to meet the taxi, and we back. &lt;br /&gt;&lt;br /&gt;When I daring enough to look at the time. The dashboard display was showing an airbag warning so the time is not showing. Maybe that was not a bad news after all.&lt;br /&gt;&lt;br /&gt;The train arrived just when the taxi waiting for oncoming traffic so to turn right on the road and got into station. Then I found I have no money to pay the additional taxi fare. I have got only got a fiver, which paid to the driver already - with additional round trip - I have got no money. That is why I need Danni to get some cash. &lt;br /&gt;&lt;br /&gt;On Phone asked Danni to get onboard first. With so many things, it was just nightmare to move things on its own.  Danni asked a staff member to hold the train for 1 minute. Replied 'Sorry madam, I can’t hold a train'. It was a virgin west coast fast train. i think probably he could if it was a slower local train. They went onboard without waiting&lt;br /&gt;&lt;br /&gt;I told the driver the embarrassing truth before she pulled stop and I slam the door open. She let me off although not very happy - I won't blame her. I thanked her very much and promised will pay back once I am back. &lt;br /&gt;&lt;br /&gt;Got the laptop bag, and cuddling the other huge rucksack from the boot, desperately run to the platform. Luckily it was at platform 1, so no need to jump down rail track or run through the passenger bridge. &lt;br /&gt;&lt;br /&gt;The train was still there, first class door was still open, right in front. Before I dove into the coach, I asked the staff 'Are they on?' he smiled and nodded, ‘Yes, they have’.&lt;br /&gt;&lt;br /&gt;The train was 2 minutes late, and probably been hold for 15 or 30 sec. &lt;br /&gt;&lt;br /&gt;Danni was very cool in the situation, and Ryan was very helpful, no crying whatsoever. When they were on, Danni found him had already napped away.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-1764301461237588904?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/1764301461237588904/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=1764301461237588904' title='1 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/1764301461237588904'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/1764301461237588904'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2008/01/almost-missed-flight-to-hong-kong.html' title='Almost missed the flight to Hong Kong'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><thr:total>1</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-2297847647805794729</id><published>2007-12-21T21:28:00.001Z</published><updated>2007-12-21T21:30:18.495Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='photography'/><title type='text'>using slide duplicator to 'scan' slide</title><content type='html'>&lt;div style="float: right; margin-left: 10px; margin-bottom: 10px;"&gt; &lt;a href="http://www.flickr.com/photos/i-fotos/2125297217/" title="photo sharing"&gt;&lt;img src="http://farm3.static.flickr.com/2130/2125297217_f5d8eaf09b_m.jpg" alt="" style="border: solid 2px #000000;" /&gt;&lt;/a&gt; &lt;br /&gt; &lt;span style="font-size: 0.9em; margin-top: 0px;"&gt;  &lt;a href="http://www.flickr.com/photos/i-fotos/2125297217/"&gt;using slide duplicator to 'scan' slide&lt;/a&gt;  &lt;br /&gt;  Originally uploaded by &lt;a href="http://www.flickr.com/people/i-fotos/"&gt;Jingye&lt;/a&gt; &lt;/span&gt;&lt;/div&gt;At old school, slide duplicator is used to copy and make additional slide set from existing ones. &lt;br /&gt;At new age, digitalise slides are done by using film scanner. &lt;br /&gt;This is an attempt to do poor man's scanning: use a full frame DSLR to copy slides to raw then process to jpg etc. I am very pleased with the result.&lt;br /&gt;It offers more control, dust control, and much faster.&lt;br /&gt;&lt;br /&gt;This one is done by using slide duplicator:&lt;br /&gt;&lt;a href="http://www.flickr.com/photos/i-fotos/2127692128/" title="Morning bath by Jingye, on Flickr"&gt;&lt;img src="http://farm3.static.flickr.com/2361/2127692128_7f04fa1887.jpg" width="333" height="500" alt="Morning bath" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;This one is done by scanner:&lt;br /&gt;&lt;a href="http://www.flickr.com/photos/i-fotos/451402373/" title="Sikh Golden Temple by Jingye, on Flickr"&gt;&lt;img src="http://farm1.static.flickr.com/183/451402373_b57731b43e.jpg" width="335" height="500" alt="Sikh Golden Temple" /&gt;&lt;/a&gt;&lt;br clear="all" /&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-2297847647805794729?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/2297847647805794729/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=2297847647805794729' title='1 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/2297847647805794729'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/2297847647805794729'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2007/12/using-slide-duplicator-to-slide.html' title='using slide duplicator to &amp;#39;scan&amp;#39; slide'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><media:thumbnail xmlns:media='http://search.yahoo.com/mrss/' url='http://farm3.static.flickr.com/2130/2125297217_f5d8eaf09b_t.jpg' height='72' width='72'/><thr:total>1</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-2324457764579120144</id><published>2007-08-19T17:15:00.000+01:00</published><updated>2007-08-19T17:32:15.305+01:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='photography'/><title type='text'>Cleanig DSLR CMOS Sensor</title><content type='html'>There is one practical issue Digital Single Lenses Reflection Camera (DSLR) lost to ‘Analogue’ (Film) SLR is dust control. DSLR attracts and accumulates dust to its CCD/CMOS sensor. A dirty sensor casts greyish dots on the photo. &lt;span style=""&gt; &lt;/span&gt;Film camera doesn’t have a CCD sensor. When shutter opens, it exposes light-sensitive film. If there is no film loaded, no film to collect dust. So even if the maybe speck fells on the film, it will 1) washed away in developing; and 2) it wouldn’t be a lasting problem.    &lt;p class="MsoNormal"&gt;I have been suffering from this ‘dirty’ problem since I converted to DSLR. I use a few zoom lenses and swap them on times. In a sun-scorched, dusty tropical countryside mounting lenses is the best thing you could do to damage your DSLR,, which was assembled in a static-free lab.&lt;/p&gt;    &lt;p class="MsoNormal"&gt;&lt;o:p&gt;&lt;/o:p&gt;I was getting-by with an incompetence bush blower in the past. Let camera camber face down while blowing air into it. I have even tried household vacuum cleaner – not to the extent stick it into the camber though. They just never went away. In fact I see more and more dots shown on the shoots. &lt;/p&gt;    &lt;p class="MsoNormal"&gt;Using Photoshop stamp tool to copy some pixels from neighbourhood is one way to get around the problem. Until there are just too many of them!&lt;/p&gt;    &lt;p class="MsoNormal"&gt;This photo was taken last Sunday with F-stop to F13, focus to more than 10 meters. It is just too dusty and too moral busty to be manually fixed (although I still did it). It made me decide to splash out on a proper cleaning kit.&lt;/p&gt;  &lt;p class="MsoNormal"&gt;&lt;o:p&gt;&lt;a href="http://www.flickr.com/photos/i-fotos/1171593612/" title="Photo Sharing"&gt;&lt;img src="http://farm2.static.flickr.com/1023/1171593612_42cef7e77f.jpg" width="500" height="333" alt="Lots of Dust" /&gt;&lt;/a&gt; &lt;br&gt; link to a &lt;a href="http://www.flickr.com/photo_zoom.gne?id=1171593612&amp;size=o"&gt;larger one&lt;/a&gt;&lt;/o:p&gt;&lt;/p&gt;  &lt;p class="MsoNormal"&gt;Here is the major steps:&lt;/p&gt;  &lt;ol style="margin-top: 0cm;" start="1" type="1"&gt;&lt;li class="MsoNormal" style=""&gt;Blow      off loose dust from the camber&lt;/li&gt;&lt;li class="MsoNormal" style=""&gt;grab      speck directly from the CCD sensor&lt;/li&gt;&lt;li class="MsoNormal" style=""&gt;Use Pec      Pad with ‘Eclipse 2’ solvent to wipe the sensor surface.&lt;/li&gt;&lt;/ol&gt;    &lt;p class="MsoNormal"&gt;&lt;o:p&gt; &lt;/o:p&gt;&lt;br /&gt;Here is tool list:&lt;/p&gt;  &lt;ul&gt;&lt;li&gt;New Giottos Q Ball Air Dust Blower Puffer with Adj tube&lt;/li&gt;&lt;li&gt;Speck Grabber Pro cleaning tool for CCD's, optics etc&lt;/li&gt;&lt;li&gt;Eclipse E2 Cleaning Fluid for camera CCD Sensor&lt;/li&gt;&lt;li&gt;PEC PAD 10x10cm (100) Cleaning Wipes for Lens &amp; Filters&lt;/li&gt;&lt;li&gt;Sensor Swab Type 3 (12Pk) For Canon, Kodak CCD Cleaning&lt;o:p&gt; &lt;/o:p&gt;&lt;br /&gt;&lt;/li&gt;&lt;/ul&gt;            &lt;p class="MsoNormal"&gt;In total it costs near £70 from eBay. Almost a third of a Canon DSLR 400D!&lt;/p&gt;    &lt;p class="MsoNormal"&gt;&lt;o:p&gt;&lt;/o:p&gt;&lt;a href="http://www.flickr.com/photos/i-fotos/1171594516/" title="Photo Sharing"&gt;&lt;img src="http://farm2.static.flickr.com/1332/1171594516_f6c5c5089f.jpg" width="457" height="500" alt="DSLR Sensor cleaning" /&gt;&lt;/a&gt;&lt;br&gt;&lt;br /&gt;&lt;/p&gt;&lt;p class="MsoNormal"&gt;Giottos Q Ball Air Dust Blower is very powerful but no as powerful as canned air, which spreads strong current may actually leaves an un-removable marks on the surface. There is an air inlet valve prevents backflow and dust coming to blower.&lt;/p&gt;    &lt;p class="MsoNormal"&gt;&lt;a href="http://www.flickr.com/photos/i-fotos/1171595430/" title="Photo Sharing"&gt;&lt;img src="http://farm2.static.flickr.com/1201/1171595430_f69ee1075e.jpg" width="500" height="370" alt="DSLR Sensor cleaning" /&gt;&lt;/a&gt;&lt;br&gt;&lt;br /&gt;&lt;/p&gt;&lt;p class="MsoNormal"&gt;Speck Grabber is use to grab visible speck directly from delicate surface, such like reflection mirror, focus screen or CMOS sensor. It is an interesting tool. It has a tacky tip (the blue tip in the picture) made of copolymer plastic. Although it has tacky adhesion property, it doesn’t leave residue on the surface it touches. &lt;/p&gt;  &lt;p class="MsoNormal"&gt;For grabbing speck directly there are other competing products, such like a ‘Dust-Aid’. Very expensive though – around 35 pounds of 12 sticky pads. &lt;/p&gt;    &lt;p class="MsoNormal"&gt;&lt;o:p&gt;&lt;a href="http://www.flickr.com/photos/i-fotos/1171596316/" title="Photo Sharing"&gt;&lt;img src="http://farm2.static.flickr.com/1002/1171596316_bafcd82fab.jpg" width="500" height="384" alt="DSLR Sensor cleaning" /&gt;&lt;/a&gt;&lt;br&gt;&lt;/o:p&gt;&lt;br /&gt;Sensor Swab is the most expensive one, costs £33. Any if you wonder what is in it – A sensor swab is a plastic wand wrapped with a Pec Pad tissue (1/3 sheet of it to be precise). &lt;span style=""&gt; &lt;/span&gt;Pec Pad is secured to the wand by a tiny elastic band. 12 units of Sensor Swab in the package, in individual seal package. So it works out to be around £2.75 a pot! IMO, this can only be justified by the made to size wand. it fits just right to the size of sensor surface, so one wipe stroke will be enough hence reduce the need of repeat wiping – which may let small speck to scratch &amp; grind the ultra sensitive sensor. &lt;/p&gt;    &lt;p class="MsoNormal"&gt;&lt;o:p&gt;&lt;a href="http://www.flickr.com/photos/i-fotos/1171597254/" title="Photo Sharing"&gt;&lt;img src="http://farm2.static.flickr.com/1358/1171597254_d60a27a7e8.jpg" width="500" height="422" alt="DSLR Sensor cleaning" /&gt;&lt;/a&gt;&lt;/o:p&gt;&lt;br /&gt;And finally lint –free Pec Pad and Eclipse 2 Optic Cleaning Fluid for Tin Oxide Coated Sensor.&lt;/p&gt;&lt;p class="MsoNormal"&gt;Now here is how to do it, reference to &lt;a href="http://www.pbase.com/copperhill/image/71784128"&gt;http://www.pbase.com/copperhill/image/71784128&lt;/a&gt; on how to prepare a home made sensor swab and how to apply it in great detail. Read it for definitive guide and tips.&lt;/p&gt;&lt;p class="MsoNormal"&gt;Before apply Sensor swab I have few more steps:&lt;/p&gt;&lt;p class="MsoNormal"&gt;1. Cleaning mirror and focus screen. Though cleaning this has no effect on shots, it helps to a cleaner view finder and reduces the risk of loose dust move to sensor later.&lt;/p&gt;  &lt;ol&gt;&lt;li&gt;Un-mounted lenses but don’t switch on ‘cleaning sensor’ function or lifting up mirror. &lt;/li&gt;&lt;li&gt;Camera face down, blow off loose dust from the camber. Be careful don’t let nozzle touch any element in the camber.&lt;/li&gt;&lt;li&gt;Use SpeckGrabber to catch each visible dust particle. Must follow it’s user guide. &lt;/li&gt;&lt;/ol&gt;        &lt;p class="MsoNormal"&gt;&lt;o:p&gt; &lt;/o:p&gt;2. Cleaning CMOS sensor.&lt;/p&gt;  &lt;ol&gt;&lt;li&gt;Lifting up mirror by B-stop or ‘cleaning sensor’ function of the camera.&lt;/li&gt;&lt;li&gt;Camera face down, use blower to blow off any loose dust speck.&lt;/li&gt;&lt;li&gt;Use SpeckGrabber to catch visible dust particle.&lt;/li&gt;&lt;li&gt;Use Sensor Swab to wipe clean the sensor, carefully.&lt;/li&gt;&lt;li&gt;Mount the lenses and release the locked-up mirror.&lt;/li&gt;&lt;/ol&gt;            &lt;p class="MsoNormal"&gt;&lt;o:p&gt;&lt;/o:p&gt;This cleaning process may need to repeat to get the best result due to lenses mounting, locked-up mirror release could bring in ‘new’ specks. &lt;/p&gt;&lt;p class="MsoNormal"&gt;If this is the case, in second run, you don’t need to clean mirror and focus screen again. So you should:&lt;/p&gt;  &lt;ol&gt;&lt;li&gt;&lt;!--[if !supportLists]--&gt;&lt;span style=""&gt;&lt;span style=""&gt;&lt;span style="font-family: &amp;quot;Times New Roman&amp;quot;; font-style: normal; font-variant: normal; font-weight: normal; font-size: 7pt; line-height: normal; font-size-adjust: none; font-stretch: normal;"&gt;&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;!--[endif]--&gt;Have every tool ready to use.&lt;/li&gt;&lt;li&gt;&lt;!--[if !supportLists]--&gt;&lt;span style=""&gt;&lt;span style=""&gt;&lt;span style="font-family: &amp;quot;Times New Roman&amp;quot;; font-style: normal; font-variant: normal; font-weight: normal; font-size: 7pt; line-height: normal; font-size-adjust: none; font-stretch: normal;"&gt;&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;!--[endif]--&gt;While lenses is mounted, locked-up mirror or switch on ‘cleaning function’.&lt;/li&gt;&lt;li&gt;&lt;!--[if !supportLists]--&gt;&lt;span style=""&gt;&lt;span style=""&gt;&lt;/span&gt;&lt;/span&gt;Detached lenses&lt;/li&gt;&lt;li&gt;&lt;!--[if !supportLists]--&gt;&lt;span style=""&gt;&lt;span style=""&gt;&lt;span style="font-family: &amp;quot;Times New Roman&amp;quot;; font-style: normal; font-variant: normal; font-weight: normal; font-size: 7pt; line-height: normal; font-size-adjust: none; font-stretch: normal;"&gt;&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;!--[endif]--&gt;Clean with SpeckGrabber if the new dust isn’t as serious as prevous.&lt;/li&gt;&lt;li&gt;&lt;!--[if !supportLists]--&gt;&lt;span style=""&gt;&lt;span style=""&gt;&lt;/span&gt;&lt;/span&gt;Use Swab&lt;/li&gt;&lt;/ol&gt;            &lt;p class="MsoNormal"&gt;This is a photo I took (F22) after first run, there is a new speck introduced while ‘old’ ones had gone.&lt;/p&gt;&lt;p class="MsoNormal"&gt;&lt;a href="http://www.flickr.com/photos/i-fotos/1170728649/" title="Photo Sharing"&gt;&lt;img src="http://farm2.static.flickr.com/1075/1170728649_a781117234.jpg" width="500" height="333" alt="still one to go" /&gt;&lt;/a&gt;&lt;br&gt;Link to a &lt;a href="http://www.flickr.com/photo_zoom.gne?id=1170728649&amp;size=o"&gt;large size&lt;/a&gt;&lt;br /&gt;&lt;/p&gt;        &lt;p class="MsoNormal"&gt;&lt;o:p&gt;&lt;/o:p&gt;This is a photo I took after second run. No speck or greyish dust anymore.&lt;br /&gt;&lt;o:p&gt; &lt;/o:p&gt;&lt;/p&gt;&lt;p class="MsoNormal"&gt;&lt;o:p&gt;&lt;a href="http://www.flickr.com/photos/i-fotos/1171587904/" title="Photo Sharing"&gt;&lt;img src="http://farm2.static.flickr.com/1305/1171587904_b8b9fac0ea.jpg" width="500" height="333" alt="no dust == world peace!" /&gt;&lt;/a&gt;&lt;br&gt;Link to a &lt;a href="http://www.flickr.com/photo_zoom.gne?id=1171587904&amp;size=o"&gt;large size&lt;/a&gt;&lt;/o:p&gt;&lt;br /&gt;World peace!&lt;/p&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-2324457764579120144?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='related' href='http://www.pbase.com/copperhill/image/71784128' title='Cleanig DSLR CMOS Sensor'/><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/2324457764579120144/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=2324457764579120144' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/2324457764579120144'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/2324457764579120144'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2007/08/cleanig-dslr-cmos-sensor.html' title='Cleanig DSLR CMOS Sensor'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><media:thumbnail xmlns:media='http://search.yahoo.com/mrss/' url='http://farm2.static.flickr.com/1023/1171593612_42cef7e77f_t.jpg' height='72' width='72'/><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-4306412285304897928</id><published>2007-08-07T08:14:00.001+01:00</published><updated>2007-08-07T08:20:35.815+01:00</updated><title type='text'>Ely Cathedral</title><content type='html'>&lt;div style="float: right; margin-left: 10px; margin-bottom: 10px;"&gt; &lt;a href="http://www.flickr.com/photos/i-fotos/1031896127/" title="photo sharing"&gt;&lt;img src="http://farm2.static.flickr.com/1176/1031896127_1cc106a3cb_m.jpg" alt="" style="border: 2px solid rgb(0, 0, 0);" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;span style="margin-top: 0px;font-size:0;" &gt;  &lt;a href="http://www.flickr.com/photos/i-fotos/1031896127/"&gt;Ely Cathedral&lt;/a&gt; &lt;br /&gt; Originally uploaded by &lt;a href="http://www.flickr.com/people/i-fotos/"&gt;Jingye&lt;/a&gt; &lt;/span&gt;&lt;/div&gt;Lady's Chapel Ely Cathedral. Dedicated to Virgin Mary. The largest of its kind in Europe. All four walls are engraved with delicate statues, unfortunately, all have been defaced in 16th century.&lt;br /&gt;&lt;br /&gt;I like the mysterious air set in this photo.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-4306412285304897928?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/4306412285304897928/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=4306412285304897928' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/4306412285304897928'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/4306412285304897928'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2007/08/ely-cathedral.html' title='Ely Cathedral'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><media:thumbnail xmlns:media='http://search.yahoo.com/mrss/' url='http://farm2.static.flickr.com/1176/1031896127_1cc106a3cb_t.jpg' height='72' width='72'/><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-4141400059188220789</id><published>2007-05-18T08:26:00.000+01:00</published><updated>2007-05-18T08:30:27.043+01:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='photography'/><title type='text'>Sikh Golden Temple</title><content type='html'>&lt;div&gt;&lt;a title="photo sharing" href="http://www.flickr.com/photos/i-fotos/451402373/"&gt;&lt;img style="border: 2px solid rgb(0, 0, 0);" alt="" src="http://farm1.static.flickr.com/183/451402373_b57731b43e_m.jpg" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;span style="font-size:0;"&gt;&lt;a href="http://www.flickr.com/photos/i-fotos/451402373/"&gt;Sikh Golden Temple&lt;/a&gt;&lt;br /&gt;&lt;/span&gt;&lt;/div&gt;&lt;br /&gt;&lt;p&gt;This photo has recently been selected as the winner of the theme &lt;a href="http://www.flickr.com/groups/the_world_through_my_eyes/discuss/72157600202319995/"&gt;‘Tourist attractions from your travels’&lt;/a&gt;&lt;br /&gt;by flickr group &lt;a href="http://www.flickr.com/groups/the_world_through_my_eyes/"&gt;‘The world though my eyes’&lt;/a&gt; and blogged &lt;a href="http://theworldthroughmyeyesgroup.blogspot.com/"&gt;here&lt;/a&gt;.&lt;br /&gt;&lt;/p&gt;&lt;p&gt;&lt;i&gt;‘This photo from the "tourist attraction" travel thread made a real impression on me. The tranquility, elegance and reverence of this shot is something to behold.’&lt;/i&gt;&lt;br /&gt;&lt;/p&gt;&lt;p&gt;I am thrilled and very happy.&lt;br /&gt;&lt;br /&gt;You can see more photos of Sikh Golden Temple &lt;a href="http://www.flickr.com/photos/i-fotos/sets/72157600059760055/"&gt;here&lt;/a&gt; &lt;/p&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-4141400059188220789?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='related' href='http://www.flickr.com/photos/i-fotos/sets/72157600059760055/' title='Sikh Golden Temple'/><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/4141400059188220789/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=4141400059188220789' title='1 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/4141400059188220789'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/4141400059188220789'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2007/05/sikh-golden-temple.html' title='Sikh Golden Temple'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><media:thumbnail xmlns:media='http://search.yahoo.com/mrss/' url='http://farm1.static.flickr.com/183/451402373_b57731b43e_t.jpg' height='72' width='72'/><thr:total>1</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-1964593288180982124</id><published>2007-05-04T22:20:00.000+01:00</published><updated>2007-05-04T23:12:21.095+01:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Java'/><title type='text'>Jetty 6.1.2 (rc2) don't do multi core processor</title><content type='html'>&lt;p class="MsoNormal"&gt;Recently we upgraded our work laptop to Intel dual core processor.&lt;br /&gt;&lt;br /&gt;After moving my local working code branch to new pc, I start to see some very strange things happened. In some tests where the web server issues an httpClient call to itself hangs indefinitely. No time out; no response, the thread is just suspended.&lt;br /&gt;&lt;br /&gt;In comparison, the very same code runs merrily on my old pc (single core), I can see the httpClient request invokes a new thread on itself.&lt;br /&gt;&lt;br /&gt;Adding the mystery, the problem on dual core pc is intermittent- in about 20% occasion it starts a new thread.&lt;/p&gt;  &lt;p class="MsoNormal"&gt;Jetty doesn't spawn a new thread on multi core CPU. Looking back I can come to this conclusion but the process to get to here wasn’t easy. Then I google out this &lt;a href="http://jira.codehaus.org/browse/JETTY-305"&gt;bug report&lt;/a&gt;&lt;br /&gt;&lt;/p&gt;    &lt;p class="MsoNormal"&gt;I quickly upgrading to Jetty 1.6.3 - the stable build just released, the problem've gone away.&lt;br /&gt;&lt;/p&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-1964593288180982124?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='related' href='http://jira.codehaus.org/browse/JETTY-305' title='Jetty 6.1.2 (rc2) don&apos;t do multi core processor'/><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/1964593288180982124/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=1964593288180982124' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/1964593288180982124'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/1964593288180982124'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2007/05/jetty-612-rc2-dont-do-multi-core.html' title='Jetty 6.1.2 (rc2) don&apos;t do multi core processor'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-3866917705787088916</id><published>2007-04-22T10:22:00.000+01:00</published><updated>2007-04-23T21:22:34.074+01:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='photography'/><category scheme='http://www.blogger.com/atom/ns#' term='not work'/><title type='text'>Macro Photography</title><content type='html'>&lt;a title="photo sharing" href="http://www.flickr.com/photos/i-fotos/467575566/"&gt;&lt;img style="BORDER-RIGHT: #000000 2px solid; BORDER-TOP: #000000 2px solid; BORDER-LEFT: #000000 2px solid; BORDER-BOTTOM: #000000 2px solid" alt="" src="http://farm1.static.flickr.com/223/467575566_27599c339c.jpg" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;span style="font-size:85%;"&gt;0.005sec (1/200); f/13; Focal Length:105 mm; ISO Speed:640;Exposure Bias:0 EV;Flash fired; using 12 and 20mm extension tube&lt;br /&gt;&lt;/span&gt;&lt;br /&gt;Received Kenko extension tube set this week. Today I have a play with it.&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;p&gt;My favourite subject is ladybird. Though very small, it is a very beautiful beetle with bright red shell doted. The size–about 5-7mm-presents a serious challenge for macro photography.&lt;/p&gt;&lt;p&gt;Back earlier April, I used Macro function comes with the lenses for close up shooting, which can be manually focus (with moving camera back and forth) at around 0.45m distance. The finished shoots after crop and interpolation(up size of the digital image by calculated and filling the pixels) become blur at edges. This is understandable-the finished photo I used as desktop is actually 4 times the life size by digital up scaling, counting the actual projection size of the beetle on the CCD sensor(or film emersion) it is much smaller. Later I will show you image magnification ratio chart.&lt;/p&gt;&lt;a title="photo sharing" href="http://www.flickr.com/photos/i-fotos/444868958/"&gt;&lt;img style="BORDER-RIGHT: #000000 2px solid; BORDER-TOP: #000000 2px solid; BORDER-LEFT: #000000 2px solid; BORDER-BOTTOM: #000000 2px solid" alt="" src="http://farm1.static.flickr.com/254/444868958_f888fedf20.jpg" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;span style="font-size:85%;"&gt;0.005sec (1/200); f/9; Focal Length:105 mm; ISO Speed:100;Exposure Bias:0 EV;Flash No; Using Macro function&lt;br /&gt;&lt;/span&gt;&lt;br /&gt;It must be optical magnification to solve the problem properly rather than resize the digital image. There are few solutions around, such like use reverse ring to mount a 50mm lenses reversely. Use a bellow or an extension tube. Each solution has its pros and corns.&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;p&gt;Reverse ring is the cheapest solution. you can pick up one from eBay for around £5 including postage from China. It exposed the lenses inside out, without proection to the lenses element it could be a hazardous. And of course you lost TTL metering and auto focus.&lt;/p&gt;&lt;p&gt;Bellow is the most flexible but quite bulky. It takes a platform with ruler and guiding rails. I feel it is not the best choose for field shooting. I saw one on eBay going for £160 with a compliment 50mm FD lenses. A new one without lenses shipped from China costs about 30 pounds includes p&amp;p.&lt;/p&gt;&lt;p&gt;That leaves candidate extension tube. By mounting it ( or combine a few and) to camera body, then mount lenses to it, you have the balance of flexibility, portable and lenses protection.&lt;br /&gt;There are two types of extension tubes around. The economical one costs around £10 pounds, it doesn’t come with electronic contact points, so the camera and your AF, TTL lenses are disconnected. The one I brought made by Kenko comes with build-in contact points, it relays the communication between lenses and camera body. So it retains TTL metering and auto focusing. Costs £55 pounds from HK. About the price I paid for a 50mm 1.8F prime lenses. Consider there is no lenses, no motor and no circuit board but just 3 aluminium rings, it is quite expensive.&lt;br /&gt;&lt;a title="photo sharing" href="http://www.flickr.com/photos/i-fotos/467588788/"&gt;&lt;img style="BORDER-RIGHT: #000000 2px solid; BORDER-TOP: #000000 2px solid; BORDER-LEFT: #000000 2px solid; BORDER-BOTTOM: #000000 2px solid" alt="" src="http://farm1.static.flickr.com/168/467588788_836f82d8f8_m.jpg" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;span style="font-size:85%;"&gt;shown with 12, 20 and 36mm extension tubes mounted (See the red dots behind the lenses?)&lt;br /&gt;&lt;/span&gt;&lt;br /&gt;Anyway I am quite excited to have a new gadget under my belt.&lt;br /&gt;&lt;br /&gt;Global warming speeds up this Spring. Back three weeks ago there are a lot of ladybirds around our garden, now they all seemed gone away. So it is very lucky I found a fella basking sun in the grass.&lt;br /&gt;&lt;br /&gt;First I mounted a 25mm tube and set our little friend to a tulip leave. Didn’t use flash as the sunlight was still strong. Auto-focus is usable, but not very useful as the field of depth is very shallow regardless aperture: a little motion from the subject will mean refocusing. And the auto focusing is just not fast enough to cope. The strong wind didn’t help neither. With the magnifying effect from the tube, it renders subject violent movement.&lt;br /&gt;&lt;br /&gt;After a few attempts, I retreated. Took my little model with the stem he is resting on and set the shooting studio over dinning table.&lt;br /&gt;&lt;br /&gt;I use flash mounted with diffuser. First I try 25mm, then 25mm plus 12mm and finally 25mm plus 12mm plus 36mm. At the beginning I didn’t bother to set up tripod, thinking with speed at 1/200 and image stabiliser, it should be alright without – I was wrong, later I checked the photos and found there are compromised on quality. &lt;/p&gt;&lt;p&gt;With all three tubes mounted, the Maginification ratio increased to 6.1 for a 50mm lenses. I zoomed to around 100mm so the shake from the hands were even apparent. So a tripod is a must. In fact I use release cable and set the custom function to enable mirror lockup.&lt;br /&gt;&lt;br /&gt;&lt;a title="photo sharing" href="http://www.flickr.com/photos/i-fotos/467586861/"&gt;&lt;img style="BORDER-RIGHT: #000000 2px solid; BORDER-TOP: #000000 2px solid; BORDER-LEFT: #000000 2px solid; BORDER-BOTTOM: #000000 2px solid" alt="" src="http://farm1.static.flickr.com/203/467586861_4c48ad54a6.jpg" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;span style="font-size:85%;"&gt;0.005sec (1/320); f/9; Focal Length:105 mm; ISO Speed:400; Exposure Bias:-1EV;Flash No; Using 20mm extension tube&lt;/span&gt; &lt;/p&gt;&lt;a title="photo sharing" href="http://www.flickr.com/photos/i-fotos/467588415/"&gt;&lt;img style="BORDER-RIGHT: #000000 2px solid; BORDER-TOP: #000000 2px solid; BORDER-LEFT: #000000 2px solid; BORDER-BOTTOM: #000000 2px solid" alt="" src="http://farm1.static.flickr.com/215/467588415_9a899ff631.jpg" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;span style="font-size:85%;"&gt;0.005sec (1/320); f/9; Focal Length:105 mm; ISO Speed:400; Exposure Bias:-1EV;Flash fired; Using 12, 20 and 36mm extension tube &lt;/span&gt;&lt;br /&gt;&lt;p&gt;&lt;span style="font-size:85%;"&gt;After shooting, I resize the photo to be the same as the CCD size - for Canon 5D it is 23.84 x 35.8mm then measure the beetle’s size then compares to it is actual size: 6mm. Here is the actual magnification ratio chart:&lt;br /&gt;(Setup) (CCD Projection size) (Mag. ratio)&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="font-size:85%;"&gt;macro: 2.8mm 0.467 &lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="font-size:85%;"&gt;12,20 36mm ex.tube: 8.5mm 1.417 (approx.)&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="font-size:85%;"&gt;12 and 20mm ex.tube: 7.6mm 1.267&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="font-size:85%;"&gt;20mm ex.tube: 3.75mm 0.625 (approx.) &lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="font-size:85%;"&gt;P.S. Also found Cannon 5D handles high ISO noise quite well. With noise reduction switch on, it only becomes visibly grainy at 1000 or above. &lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;a href="http://www.flickr.com/photos/i-fotos/sets/72157600041367303/"&gt;My close up shooting album.&lt;/a&gt;&lt;/p&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-3866917705787088916?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='related' href='http://www.flickr.com/photos/i-fotos/sets/72157600041367303/' title='Macro Photography'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/3866917705787088916'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/3866917705787088916'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2007/04/macro-photography.html' title='Macro Photography'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><media:thumbnail xmlns:media='http://search.yahoo.com/mrss/' url='http://farm1.static.flickr.com/223/467575566_27599c339c_t.jpg' height='72' width='72'/></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-5116790887772284542</id><published>2007-01-29T00:25:00.000Z</published><updated>2007-01-29T14:07:41.954Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='configuration'/><title type='text'>Custom configuration with nested collections in .Net 2.0</title><content type='html'>I am writing this as a brain dump.&lt;br /&gt;&lt;br /&gt;Has been played around with .NET 2.0 strong type configuration this weekend (a bit late, I know). After some uneven drive-thanks to the lack of documentation- I finally produce a custom configuration file like the one below.&lt;br /&gt;&lt;br /&gt;(For my work colleagues at Talis, yeah you - I know you will check my blog – If you are wondering why I am not using the time on our project for &lt;a href="http://www.w3.org/RDF/"&gt;RDF&lt;/a&gt; Java configuration. Honestly, I do. I mean you absorb and learn from a competing technology, getting ideas from patterns, even the naming convention it uses – particularly there is Reflector for sneaking around.)&lt;br /&gt;&lt;br /&gt;Here is the custom configuration setting with nested collection:&lt;br /&gt;&lt;span style="font-family:courier new;font-size:85%;"&gt;&amp;lt;section name="workflowConfig" type="Jingye.Workflow.Exe.WorkflowConfigSectionHandler,Workflow" /&amp;gt;&lt;br /&gt;…&lt;br /&gt;&lt;br /&gt;&amp;lt;workflowConfig seperateProcesses="true" processWaitTime="50000"&amp;gt;&lt;br /&gt;&amp;lt;setup workingPath="c:\temp\" /&amp;gt;&lt;br /&gt;&amp;lt;workflow name="WorkflowOne" interval="15" dailyRun="true" startTime="09"&amp;gt;&lt;br /&gt;&amp;lt;task name="task1" onError="Abort"/&amp;gt;&lt;br /&gt;&amp;lt;task name="task2" onError="Log" /&amp;gt;&lt;br /&gt;&amp;lt;/workflow&amp;gt;&lt;br /&gt;&amp;lt;workflow name="WorkflowTwo" interval="9999" dailyRun="true" startTime="08"&amp;gt;&lt;br /&gt;&amp;lt;task name="anotherTask1" onError="Abort"/&amp;gt;&lt;br /&gt;&amp;lt;task name="anotherTask2" onError="Log" /&amp;gt;&lt;br /&gt;&amp;lt;/workflow&amp;gt;&lt;br /&gt;&amp;lt;/workflowConfig&amp;gt;&lt;br /&gt;&lt;/span&gt;&lt;br /&gt;&lt;strong&gt;Some well-known bits and bobs&lt;br /&gt;&lt;/strong&gt;1. Where is my config file?&lt;br /&gt;For web app, this setting is in web.config. It will be picked up by &lt;span style="font-family:courier new;"&gt;ConfigutationManager&lt;/span&gt; as the default config file.&lt;br /&gt;For console app or win service, you need to tell the Configuration about this file.&lt;br /&gt;1) The short form. You app.exe.config file should be side by side with app.exe. Framework will ‘intelligently’ figure out the path and suffix ‘.config’ to the exe.&lt;br /&gt;&lt;span style="font-family:courier new;font-size:85%;"&gt;Configuration config = ConfigurationManager.OpenExeConfiguration("Workflow.exe");&lt;br /&gt;WorkflowConfigSectionHandler scheduler = (WorkflowConfigSectionHandler)config.GetSection("workflowConfig");&lt;br /&gt;&lt;/span&gt;&lt;br /&gt;2) The long form. The short form wraps this long form for convenient sake, but if you want to load a config from a different location or even pass in as command line argument, these are the lines to use&lt;br /&gt;&lt;br /&gt;&lt;span style="font-family:courier new;font-size:85%;"&gt;ExeConfigurationFileMap fileMap = new ExeConfigurationFileMap();&lt;br /&gt;// relative path names possible&lt;br /&gt;fileMap.ExeConfigFilename = @"c:\temp\exe\ConfigTest.exe.config";&lt;br /&gt;// Open another config file&lt;br /&gt;Configuration config =&lt;br /&gt;ConfigurationManager.OpenMappedExeConfiguration(fileMap,&lt;br /&gt;ConfigurationUserLevel.None);&lt;br /&gt;&lt;br /&gt;//read/write from it as usual&lt;br /&gt;ConfigurationSection mySection = config.GetSection("workflowConfig");&lt;br /&gt;&lt;/span&gt;&lt;br /&gt;2. Your configuration section - the root derives from &lt;span style="font-family:courier new;font-size:85%;"&gt;System.Configuration.ConfigurationSection&lt;/span&gt;. Back in .Net 1.x era, this is traditionally called XXXXHandler as it implements IConfigurationSectionHandler interface.&lt;br /&gt;&lt;br /&gt;3. Each configuration element is declared as class derives from ConfigurationElement. Configuration element can have child elements, again derives from ConfigurationElement.&lt;br /&gt;&lt;br /&gt;4. Configration elements take attributes/properties - decorates class properties with ConfigurationProperty. However configuration element doesn’t take CDATA text as body.&lt;br /&gt;&lt;br /&gt;&lt;span style="font-family:courier new;font-size:85%;"&gt;[ConfigurationProperty("seperateProcesses", DefaultValue = "true", IsRequired = false, IsDefaultCollection = true)]&lt;br /&gt;&lt;/span&gt;&lt;br /&gt;5. Assign a key property in ConfigurationPropertyAttribute decoration. Such like ‘name’. You will need this to locate your configuration element in a MAP.&lt;br /&gt;&lt;br /&gt;6. If a config element is a collection such like this, you also need to implement a façade to manage access to each member, this MyConfigElementCollection class is derived from ConfigurationElementCollection class.&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;Less well-known bits about MyConfigElementCollection class&lt;/strong&gt;&lt;br /&gt;&lt;br /&gt;1. By default, MyConfigElementCollection uses AddRemoveClearMap as its merging semantics – meaning how machine.config and your web.config or app.exe.config should merge together.&lt;br /&gt;You can override this to be BasicMap or AddRemoveClearMapAlternate or BasicMapAlternate. Mark Gabarra discusses each of this merging semantic in his blog “&lt;a href="http://blogs.msdn.com/markgabarra/archive/2006/06/27/648742.aspx"&gt;.Net Configuration Default Behaviour&lt;/a&gt;”, worth a read if you are wondering ‘how could I stop downstream config changes my setting?’&lt;br /&gt;&lt;br /&gt;&lt;span style="font-family:courier new;font-size:85%;"&gt;public override ConfigurationElementCollectionType CollectionType&lt;br /&gt;{&lt;br /&gt;get{ return ConfigurationElementCollectionType.BasicMap;}&lt;br /&gt;}&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;2. Override ElementName, if you are not using AddRemoveClearMap or just find another &lt;span style="font-family:courier new;font-size:85%;"&gt;‘&amp;lt;add&amp;gt;’&lt;/span&gt; being confusing to the guy actually uses your app.&lt;br /&gt;By default, ElementName is “” (String.Empty), because in AddRemoveClearMapAlternate semantic, elements should be view as ‘operation instructions’ – add, remove or clear an element. The real name of the element is passed in the strong typing context, hence anonymous is acceptable. Nevertheless, it is less self-describing to the user.&lt;br /&gt;&lt;span style="font-family:courier new;font-size:85%;"&gt;protected override string ElementName&lt;br /&gt;{ get { return "workflow"; } }&lt;br /&gt;&lt;/span&gt;&lt;br /&gt;3. In the parent element, where an instance of this element or a collection of this elements is declared, give the default name – “” as the name in ConfigurationProperty.&lt;br /&gt;&lt;span style="font-family:courier new;font-size:85%;"&gt;[ConfigurationProperty("", IsRequired = false, IsDefaultCollection = true)]&lt;br /&gt;public WorkflowConfigElementCollection Workflows&lt;br /&gt;{&lt;br /&gt;get&lt;br /&gt;{ return (WorkflowConfigElementCollection)base[""]; }&lt;br /&gt;set&lt;br /&gt;{ base[""] = value; }&lt;br /&gt;}&lt;br /&gt;&lt;/span&gt;&lt;br /&gt;I find this is confusing at the beginning, but if link back to point 2, it all make sense on how reflection and serialization works.&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;Reference:&lt;br /&gt;&lt;/strong&gt;Mark Gabarra, blog “&lt;a href="http://blogs.msdn.com/markgabarra/archive/2006/06/27/648742.aspx"&gt;.Net Configuration Default Behaviour&lt;/a&gt;”&lt;br /&gt;Jason Diamond blogs on using call back custom validator: &lt;a href="http://jason.diamond.name/weblog/2006/05/25/custom-configuration-section-validator-weirdness"&gt;Custom Configuration Validator Weirdness&lt;/a&gt;&lt;br /&gt;Alois Kraus: &lt;a href="http://www.codeproject.com/useritems/SystemConfiguration.asp"&gt;Read/Write App.Config with NET 2.0&lt;/a&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-5116790887772284542?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/5116790887772284542'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/5116790887772284542'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2007/01/custom-configuration-with-nested.html' title='Custom configuration with nested collections in .Net 2.0'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-8783260231766045831</id><published>2007-01-11T18:06:00.000Z</published><updated>2007-01-12T11:59:27.785Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='not work'/><title type='text'>Five things</title><content type='html'>&lt;p&gt;Five Things about you and five firends of yours&lt;br /&gt;&lt;br /&gt;Admit that it is hard for me to come with five friends who blogg, this is difficult. And my Talisian colleagues are moving fast – I would say although your colleagues are your friends (at least in theory), you are not meant to tag them as this spirals into a workspace dead loop.&lt;br /&gt;Now I am pulling my hair for the five coz &lt;a href="http://www.dynamicorange.com/blog/archives/five_things.html"&gt;Rob&lt;/a&gt; exhausts (almost) all work-bloggers I know, thanks also goes to &lt;a href="http://iandavis.com/blog/2007/01/five-things"&gt;Ian (internet alchemy) D&lt;/a&gt; too. No, nil, zero, no one (&lt;a href="http://pragmaticintegration.blogspot.com/"&gt;Andy&lt;/a&gt;, I leave &lt;a href="http://trafficlightmusings.blogspot.com/index.html"&gt;Sarah&lt;/a&gt; to your account).&lt;/p&gt;&lt;p&gt;So if you wonder who this quietly Jingye is, here is the five of him: &lt;/p&gt;&lt;ol&gt;&lt;li&gt;I got to gym at least five times a week, do a 5km/30mins run before finishing the day.&lt;/li&gt;&lt;li&gt;I consume around 500 minutes podcast each week, mostly IT and digital photography related. My most favourite is &lt;a href="http://downloads.bbc.co.uk/rmhttp/downloadtrial/worldservice/documentaryarchive/rss.xml"&gt;BBC documentary archives &lt;/a&gt;and the least favourite is &lt;a href="www.ibm.com/services/us/igs/rss/ibm_bcs_podcast.xml"&gt;IBM Institute for Business Value&lt;/a&gt;.&lt;/li&gt;&lt;li&gt;Danni, my wife and I have recently completed a 25 km charity walk for&lt;a href="http://www.bhf.org.uk/"&gt; British Heart Foundation&lt;/a&gt; at the Peak District.&lt;/li&gt;&lt;li&gt;My latest gadget is a Canon 5D digital camera. Here is one (more are in my &lt;a href="http://www.flickr.com/photos/i-fotos/sets"&gt;flickr&lt;/a&gt;). &lt;/li&gt;&lt;li&gt;I organise outdoor activities for the alike Chinese expats in Britain. Our next call is ‘Winter Farm Experience’ at Lake District. &lt;/li&gt;&lt;/ol&gt;&lt;p&gt;&lt;a title="Photo Sharing" href="http://www.flickr.com/photos/i-fotos/340788937/"&gt;&lt;img height="248" alt="Stafford - Baswich" src="http://farm1.static.flickr.com/132/340788937_934947aaa1.jpg" width="500" /&gt;&lt;/a&gt;&lt;/p&gt;&lt;p&gt;And here are five friends of mine: &lt;a href="http://mumucoffee.spaces.live.com/Blog"&gt;mumu&lt;/a&gt;, &lt;a href="http://xmaspanda.spaces.live.com/Blog"&gt;xp&lt;/a&gt;, &lt;a href="http://flywhc.spaces.live.com/Blog"&gt;flywhc&lt;/a&gt;, &lt;a href="http://thetime.spaces.live.com/Blog/"&gt;TheTime&lt;/a&gt;, &lt;a href="http://wisherxu.spaces.live.com/blog"&gt;Sisyphus&lt;/a&gt;&lt;/p&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-8783260231766045831?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='related' href='http://www.dynamicorange.com/blog/archives/five_things.html' title='Five things'/><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/8783260231766045831/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=8783260231766045831' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/8783260231766045831'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/8783260231766045831'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2007/01/five-things.html' title='Five things'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><media:thumbnail xmlns:media='http://search.yahoo.com/mrss/' url='http://farm1.static.flickr.com/132/340788937_934947aaa1_t.jpg' height='72' width='72'/><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-7317461644809680873</id><published>2006-12-08T09:29:00.000Z</published><updated>2006-12-08T09:40:09.122Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='GLIO'/><title type='text'>Effective Writing</title><content type='html'>&lt;p&gt;Found &lt;a href="mailto:jeremystellsmith@gmail.com"&gt;Jeremy Stell-Smith&lt;/a&gt;'s &lt;a href="http://work.onemanswalk.com/articles/2006/12/08/effective-writing"&gt;Effective Writing&lt;/a&gt; a very useful guide from a TDD developer’s point of view on getting things done – without being distracted or going deviation in the writing.&lt;br /&gt;&lt;br /&gt;I still got a few travel essays pending – ‘todo’ since July - seem very daunting task, considering it is a part-time hobbits thing. In the running up to the New Year, I am going to try to apply these principles.&lt;br /&gt;&lt;br /&gt;&lt;li&gt;Work top down – do outline first&lt;br /&gt;&lt;li&gt;Question Driven Writing – compare that to test driven development to stay on topic.&lt;br /&gt;&lt;li&gt;Work in Sprints - cutting off the distraction and shut yourself down to external.&lt;br /&gt;&lt;p&gt;&lt;/p&gt;&lt;/li&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-7317461644809680873?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='related' href='http://work.onemanswalk.com/articles/2006/12/08/effective-writing' title='Effective Writing'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/7317461644809680873'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/7317461644809680873'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2006/12/effective-writing.html' title='Effective Writing'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-6256881250483349557</id><published>2006-11-11T20:49:00.000Z</published><updated>2006-11-11T20:52:30.362Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='.net'/><title type='text'>AppDomain, process and components...</title><content type='html'>This is a fundamental concept in .Net. In this short retrospective I try to offload following points:&lt;br /&gt;1. What is AppDomain? Aslo a derived question: what is the difference between Appdomain and process?&lt;br /&gt;2. Why we need AppDomain?&lt;br /&gt;3. What is the design implication of Appdomain has on software?&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight:bold;"&gt;So what is AppDomain? What is the difference between Appdomain and process?&lt;br /&gt;&lt;/span&gt;From &lt;a href="http://www.gotdotnet.com/team/clr/AppdomainFAQ.aspx#_Toc514058484"&gt;gotnotnet&lt;/a&gt; &lt;br /&gt;“Application Domain is a construct in the CLR that is the unit of isolation for an application.” In non-.NET CLR environment, each running application is hosted by a process. There can be numerous processes launched of the same application and each process can only host ONE application. In contrast, .NET CLR introduces a light-way unit to load an application – AppDomain. Each AppDomain hosts one application, (or indeed assembly, component). Each process can have multiple AppDomains.&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight:bold;"&gt;Why we need AppDomain?&lt;/span&gt;&lt;br /&gt;AppDomain provides isolation around applications without the heavy cost associated with running an application within a process (address space, context, security...). In another word when addressing security context for example, it is wrapped around process  unit. It relives each resident in an AppDomain from handling it themselves. &lt;br /&gt;&lt;br /&gt;The isolation means: &lt;br /&gt;• An application can be independently stopped.&lt;br /&gt;• An application cannot directly access code or resources in another application.&lt;br /&gt;• A fault in an application cannot affect other applications.&lt;br /&gt;• Configuration information is scoped by application. This means that an application controls the location from which code is loaded and the version of the code that is loaded.&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight:bold;"&gt;What is the design implication of AppDomain has on software?&lt;/span&gt;&lt;br /&gt;AppDomain promotes a loose-coupled component-oriented programming mode.&lt;br /&gt;&lt;br /&gt;The term component is probably one of the most overloaded terms in morden software engineering. From &lt;a href="http://en.wikipedia.org/wiki/Component"&gt;Wikipedia&lt;/a&gt; I found quite a few entries, which defines ‘component’ in different domain. Where it is related to computer science, it reads ‘&lt;span style="font-style:italic;"&gt;A piece that makes up a whole, a part of an assembly&lt;/span&gt;’. Very abstract. In electronic component, it says ‘&lt;span style="font-style:italic;"&gt;An electronic component is a basic electronic element usually packaged in a discrete form with two or more connecting leads or metallic pads. Components are intended to be connected together…&lt;/span&gt;’ This definition is more vivid to use as a metaphor here.&lt;br /&gt; &lt;br /&gt;In .net a class *IS* a component. In the extreme form, one can compile a .net class into a binary assembly. Then CLR can load it into an AppDomain of a process. &lt;br /&gt;From runtime process’ point of view, ‘traditional’ programming model/application is packaged to a monolithic binary block, regardless how it maps class diagram for business logic. Monolithic binary means they are tightly coupled. A change to one class can trigger a massive relinking of the entire application and necessitate retesting and redeployment of all other classes.&lt;br /&gt;&lt;br /&gt;In contrast, a .net component based application is a collection of binary building blocks grouped by functionality. Each block contains one or more classes. At run time, each block is loaded to an AppDomain, together, they make up a process. If one of the component needs to be update, changes are contained to that component only. No existing client of the component requires recompilation or redeployment. An updated component can even be updated while a client application is running, as long as the component isn’t currently being used.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-6256881250483349557?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/6256881250483349557'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/6256881250483349557'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2006/11/appdomain-process-and-components.html' title='AppDomain, process and components...'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-8244114360963271225</id><published>2006-11-02T18:06:00.000Z</published><updated>2006-11-02T18:31:09.503Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='nant'/><title type='text'>Create your custom xAnt task</title><content type='html'>&lt;p class="MsoNormal"&gt;Here are some notes on how to extend ant task to provide your custom ant task. &lt;/p&gt;  &lt;p class="MsoNormal"&gt;Both ant build (for Java) and nAnt build (for .net) are discussed.&lt;/p&gt;&lt;p class="MsoNormal"&gt;  &lt;/p&gt;1. nAnt&lt;br /&gt;&lt;br /&gt;In nAnt for .net build you embedded c# code as script though semantically it is a derived class from Nant.Core.Task. (You don’t need to include Nant.Core assembly. It is loaded by default). A scripting block is a top level block, meaning side by side with &amp;lt;target&amp;gt; block.&lt;br /&gt;&lt;br /&gt;In following sample script., the first static c# function is a - function - to work out number of running processes by given name.&lt;br /&gt;The secnd task class is to kick off an external batch file - if you want the batch running in a separate process there isn't better way that this cumbersome one.&lt;br /&gt;The third task class is to kill a process.&lt;br /&gt;&lt;br /&gt;&lt;span style="font-size:78%;"&gt;    &amp;lt;script language="C#" prefix="custom"&amp;gt;&lt;br /&gt;    &amp;lt;code&amp;gt;&lt;br /&gt;        &amp;lt;![CDATA[&lt;br /&gt;            [Function("NumberOfRunningProcess")]&lt;br /&gt;            public static int NumberOfRunningProcess(string name)&lt;br /&gt;            {&lt;br /&gt;                System.Diagnostics.Process[] procList =  System.Diagnostics.Process.GetProcessesByName(name);&lt;br /&gt;                return procList.Length;&lt;br /&gt;            }&lt;br /&gt;&lt;br /&gt;            [TaskName("WriteRunXspBatchScript")]&lt;br /&gt;            public class WriteRunXspBatchScript: Task&lt;br /&gt;            {&lt;br /&gt;                private string _batchFilePath;&lt;br /&gt;                private string _httpRootPath;&lt;br /&gt;                private int _port;&lt;br /&gt;              &lt;br /&gt;                [TaskAttribute("XspRunScript", Required=true)]&lt;br /&gt;                public string BatchFilePath&lt;br /&gt;                {&lt;br /&gt;                    get{return _batchFilePath;}&lt;br /&gt;                    set{_batchFilePath=value;}&lt;br /&gt;                }&lt;br /&gt;&lt;br /&gt;                [TaskAttribute("HttpRootPath", Required=true)]&lt;br /&gt;                public string HttpRootPath&lt;br /&gt;                {&lt;br /&gt;                    get{return _httpRootPath;}&lt;br /&gt;                    set{_httpRootPath=value;}&lt;br /&gt;                }&lt;br /&gt;&lt;br /&gt;                [TaskAttribute("Port", Required=true)]&lt;br /&gt;                public int HttpPort&lt;br /&gt;                {&lt;br /&gt;                    get{return _port;}&lt;br /&gt;                    set{_port=value;}&lt;br /&gt;                }&lt;br /&gt;&lt;br /&gt;                protected override void ExecuteTask()&lt;br /&gt;                {&lt;br /&gt;                    string cmd = string.Format("start /MIN  xsp --root \"{0}\" --port {1}", _httpRootPath, _port);&lt;br /&gt;                    using (StreamWriter wr = new StreamWriter(_batchFilePath,false))&lt;br /&gt;                    {&lt;br /&gt;                        wr.WriteLine("@echo off");&lt;br /&gt;                        wr.WriteLine(cmd);&lt;br /&gt;                    }&lt;br /&gt;                }&lt;br /&gt;            }          &lt;br /&gt;            [TaskName("StopXsp")]&lt;br /&gt;            public class StopXsp : Task{&lt;br /&gt;                private bool _deleteXsp;&lt;br /&gt;                private string _xspRunScript;&lt;br /&gt;              &lt;br /&gt;                [TaskAttribute("DeleteXspRunScript", Required=false)]&lt;br /&gt;                public bool DeleteXspRunScript&lt;br /&gt;                {&lt;br /&gt;                    get{return _deleteXsp;}&lt;br /&gt;                    set{_deleteXsp=value;}&lt;br /&gt;                }&lt;br /&gt;&lt;br /&gt;                [TaskAttribute("XspRunScript", Required=false)]&lt;br /&gt;                public string XspRunScript&lt;br /&gt;                {&lt;br /&gt;                    get{return _xspRunScript;}&lt;br /&gt;                    set{_xspRunScript=value;}&lt;br /&gt;                }&lt;br /&gt;          &lt;br /&gt;                protected override void ExecuteTask() {&lt;br /&gt;                    System.Diagnostics.Process[] procList =  System.Diagnostics.Process.GetProcessesByName("mono");&lt;br /&gt;                    if (procList==null )&lt;br /&gt;                    {&lt;br /&gt;                        throw new Exception("No Mono process found. Expect to kill one and only one mono xsp process");&lt;br /&gt;                    }&lt;br /&gt;                    if (procList.Length&amp;gt;1)&lt;br /&gt;                    {&lt;br /&gt;                        throw new Exception("More than one Mono processes is running. Expect to kill one and only one mono xsp process");&lt;br /&gt;                    }&lt;br /&gt;                    try&lt;br /&gt;                    {&lt;br /&gt;                        procList[0].Kill();&lt;br /&gt;                    }&lt;br /&gt;                    catch(Exception){;}&lt;br /&gt;              &lt;br /&gt;                    if (_deleteXsp)&lt;br /&gt;                    {&lt;br /&gt;                        File.Delete(_xspRunScript);&lt;br /&gt;                    }&lt;br /&gt;                }&lt;br /&gt;            }&lt;br /&gt;        ]]&amp;gt;&lt;br /&gt;    &amp;lt;/code&amp;gt;&lt;br /&gt;&amp;lt;/script&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-size:100%;"&gt;&lt;span style="font-weight: bold;"&gt;Usage:&lt;/span&gt;&lt;br /&gt;&lt;span style="font-size:78%;"&gt;&amp;lt;echo message="process devenv ${custom::NumberOfRunningProcess('devenv')}" /&amp;gt;&lt;br /&gt;&amp;lt;WriteRunXspBatchScript Port="80" HttpRootPath="${webcontrolsUnitTest.src.dir}" XspRunScript="${build.dir}\${MonoXspRun}" /&amp;gt;&lt;br /&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style="font-size:78%;"&gt;&amp;lt;&lt;/span&gt;&lt;span style="font-size:78%;"&gt;StopXsp DeleteXspRunScript="true" XspRunScript="${build.dir}\${MonoXspRun}"/&lt;/span&gt;&lt;span style="font-size:78%;"&gt;&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="font-size:100%;"&gt;&lt;br /&gt;2. ant&lt;br /&gt;Reference to &lt;a href="http://www-128.ibm.com/developerworks/java/library/j-antbuild/"&gt;Extending Ant to support interactive builds&lt;/a&gt;,  to archive this you need to write external java classes, expose package via classpath by system envronment variable or via &amp;lt;path&amp;gt; in the build script.&lt;br /&gt;&lt;br /&gt;The only change to the sample code given in &lt;/span&gt;&lt;span style="font-size:100%;"&gt;&lt;a href="http://www-128.ibm.com/developerworks/java/library/j-antbuild/"&gt;Extending Ant to support interactive builds&lt;/a&gt; is instead of using classpath, it uses &lt;/span&gt;&lt;span style="font-size:100%;"&gt;&lt;span style="font-weight: bold;"&gt;&amp;lt;path&amp;gt;&lt;/span&gt; :&lt;br /&gt;&lt;span style="color: rgb(51, 51, 153);font-size:78%;" &gt;&amp;lt;?xml version="1.0"?&amp;gt;&lt;br /&gt;&amp;lt;project name="PropertyPromptExample" default="main" basedir="."&amp;gt;&lt;br /&gt;  &amp;lt;property name="promptTimeout" value="5"/&amp;gt;&lt;br /&gt;  &amp;lt;path id="extendedTask"&amp;gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;         &amp;lt;fileset dir="c:\playpit\"&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;           &amp;lt;include name="monkeyNuts.jar"/&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;       &amp;lt;/fileset&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;   &amp;lt;/path&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;   &amp;lt;taskdef name="propertyprompt" classname="com.ibm.samples.apache.tools.ant.taskdefs.optional.PropertyPrompt" classpathref="extendedTask"/&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;  &amp;lt;target name="main"&amp;gt;&lt;br /&gt;&amp;lt;!--    &amp;lt;javac srcdir="." destdir="." verbose="on"/&amp;gt;   --&amp;gt;&lt;br /&gt;  &amp;lt;property name="propA" value="oldValA"/&amp;gt;&lt;br /&gt;  &amp;lt;property name="propA" value="oldValA1"/&amp;gt;&lt;br /&gt;  &amp;lt;echo&amp;gt;value of propA: ${propA}&amp;lt;/echo&amp;gt;&lt;br /&gt;  &amp;lt;echo&amp;gt;value of propB: ${propB}&amp;lt;/echo&amp;gt;&lt;br /&gt;  &amp;lt;propertyprompt propertyname="propA" promptcharacter=":"&amp;gt;Enter value for propA&amp;lt;/propertyprompt&amp;gt;&lt;br /&gt;  &amp;lt;propertyprompt propertyname="propB" defaultvalue="defvalB"&amp;gt;What is the value for propB&amp;lt;/propertyprompt&amp;gt;&lt;br /&gt;  &amp;lt;echo&amp;gt;value of propA: ${propA}&amp;lt;/echo&amp;gt;&lt;br /&gt;  &amp;lt;echo&amp;gt;value of propB: ${propB}&amp;lt;/echo&amp;gt;&lt;br /&gt;  &amp;lt;/target&amp;gt;&lt;br /&gt;&amp;lt;/project&amp;gt;&lt;br /&gt;&lt;/span&gt;&lt;/span&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-8244114360963271225?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/8244114360963271225'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/8244114360963271225'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2006/11/create-your-custom-xant-task.html' title='Create your custom xAnt task'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-360084643546808887</id><published>2006-10-27T17:48:00.000+01:00</published><updated>2006-10-27T18:00:40.674+01:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='photoshop tips'/><title type='text'>Export &amp; Import Goodie from/to Photoshop</title><content type='html'>&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://photos1.blogger.com/blogger2/3778/742/1600/screenshot.gif"&gt;&lt;img style="margin: 0px auto 10px; display: block; text-align: center; cursor: pointer;" src="http://photos1.blogger.com/blogger2/3778/742/400/screenshot.gif" alt="" border="0" /&gt;&lt;/a&gt;&lt;br /&gt;Just finished my retrospective notes on &lt;a href="http://jingyeluo.blogspot.com/2006/10/photoshop-action-and-batch-to-watermark.html#links"&gt;Photoshop Action and Batch to watermark images&lt;/a&gt; then I think 'wait a minute, I have all these - custom shape custom action in one pc, how do I port it to another? I don't want to repeat the manual creation work again.&lt;br /&gt;&lt;br /&gt;It is a very simple task, a quick search found that IM Photography's tips: &lt;a href="http://www.imphotography.com/downloads/installactions.htm"&gt;Installing and exporting Photoshop actions&lt;/a&gt; Likewise you can export and import custom shape by first select the shape, then click on the little play trangle at the top right corner to bring up the context menu, then select 'save shapes...'&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-360084643546808887?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='related' href='http://www.imphotography.com/downloads/installactions.htm' title='Export &amp; Import Goodie from/to Photoshop'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/360084643546808887'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/360084643546808887'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2006/10/export-import-goodie-fromto-photoshop.html' title='Export &amp; Import Goodie from/to Photoshop'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-7721808151322570346</id><published>2006-10-27T16:45:00.000+01:00</published><updated>2006-10-27T22:12:28.606+01:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='photoshop tips'/><title type='text'>Photoshop Action and Batch to watermark images</title><content type='html'>&lt;span style="font-weight: bold;font-size:78%;" &gt;Jingye says: 'I am scratching my head on Photoshop tasks'. I am not a pro (digital) photographer. With busy life, &lt;/span&gt;&lt;span style="font-weight: bold;font-size:78%;" &gt; I just want to get some reasonable quality picture from my digital cameras&lt;/span&gt;&lt;span style="font-weight: bold;font-size:85%;" &gt;&lt;span style="font-size:78%;"&gt;. I took many many photos during holidays (easliy over 5Gb for two weeks in a exotic country).  I only have time to tidy them up a little bit, mostly an auto-leveling and an auto-curving. Then I will print some, upload a small size to &lt;a href="http://www.flickr.com/photos/i-fotos"&gt;flickr&lt;/a&gt;; archive a large version.&lt;br /&gt;&lt;br /&gt;Many ps tasks I have done in the pass were forgotten fast. So here I steal/rewrite from other people’s Photoshop tips/how to do something. I claim not rights of them unless stated. This is just my web notepad for myself and everyone else.’&lt;br /&gt;&lt;br /&gt;&lt;span style="font-size:130%;"&gt;Photoshop Action and Batch to watermark images&lt;br /&gt;&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;br /&gt;Rewrite and proved based on Chris Kitchener's &lt;a href="http://www.ephotozine.com/techniques/viewtechnique.cfm?recid=339"&gt;Watermarking your photos in Photoshop 7 and CS technique&lt;/a&gt; ) and &lt;a href="http://photoshop911.typepad.com/help/2004/04/watermarking_ph.html"&gt;Watermarking Photos (batch)&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;Objective&lt;/span&gt;:&lt;br /&gt;1) Create a reusable watermark.&lt;br /&gt;2) Create a custom action and use Photoshop’s batch command to process a group of images to apply watermark.&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;&lt;br /&gt;Applicable versions&lt;/span&gt;:&lt;br /&gt;Photoshop CS (v8) and Photoshop v7&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;&lt;br /&gt;Prep work&lt;/span&gt;:&lt;br /&gt;I used transparent watermark for  protecting IP rights yet showing off  pictures. I would try to make all images looked consistent when viewed as a collection-the size, effect, position etc. For this reason, I will resize all  images to a certain size (see &lt;a href="http://jingyeluo.blogspot.com/2006/10/photoshop-action-and-batch-to-resize.html#links"&gt;Using Photoshop Actions and batch command to resize images&lt;/a&gt; &lt;span style="font-weight: bold;font-size:130%;" &gt;&lt;/span&gt;. Then group landscape and portrait photos in two source folder (i.e. source_landscape, source_portrait) 2) create two actions: e.g. ‘watermark Landscape’ ‘watermark portrait’.&lt;br /&gt;Create an ‘output’ folder as well.&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;Task 1: Create an custom shape, which will be used as watermark later.&lt;/span&gt;&lt;br /&gt;At this stage there is no need to tweak the shape yet for special effect yet, just  create a new document with plain text/logo. For example a square logo can be of &lt;span style="font-style: italic;"&gt;Width: 3 inches x Height: 3 inches,    Resolution: 300 pixels per inch (ppi) and the Colour Mode: Greyscale, Contents:    White&lt;/span&gt;, Type the text with desired font and size it to fill all canvas.&lt;br /&gt;(&lt;span style="font-weight: bold;"&gt;important&lt;/span&gt;) Go to the 'Layer' menu, highlight 'Type' and select 'Create Work Path'.          This action converts the text to an outline vector path. To add the shape          the library, choose 'Define Custom Shape' from the "Edit' menu and          name the item 'watermark'. Click 'OK'.&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;Task 2: Create Watermark&lt;/span&gt;&lt;br /&gt;1) Open a test image, ideally this should be in similar size to those will be in batch process later, pick an image that it is not too dark around watermark application area. Also consider an watermark for lanscape and portrait images each. Here I will only give lanscape images as example.&lt;br /&gt;2) In the 'Preferences', check that the 'Units and Rulers' are set to    'Inches'. 'Units' set to 'Pixels' or 'Percent' create a watermark that changes    size based on the files resolution and will prove unreliable.&lt;br /&gt;3) Add a new layer(shift+ctrl+n), nae it 'watermark'.&lt;br /&gt;3) From Toolbox, select &lt;b&gt;&lt;/b&gt;'Custom        Shape Tool' (U), found under the 'Rectangle Tool'. Select 'watermark' shape from the listed icons.&lt;br /&gt;4) Hold '&lt;span style="font-weight: bold;"&gt;shift&lt;/span&gt;' key and draw watermark on new layer to fill the entire width.&lt;br /&gt;5) (Layer menu) &lt;span style="font-weight: bold;"&gt;Rasterize&lt;/span&gt;-&gt;&lt;span style="font-weight: bold;"&gt;shape&lt;br /&gt;&lt;/span&gt;6) (Filter menu) &lt;span style="font-weight: bold;"&gt;Stylize&lt;/span&gt;-&gt;&lt;span style="font-weight: bold;"&gt;Emboss,&lt;/span&gt; angle 135&lt;br /&gt;7) (Layer menu), '&lt;span style="font-weight: bold;"&gt;Layer Style&lt;/span&gt;' -&gt;'&lt;span style="font-weight: bold;"&gt;Blending    Options&lt;/span&gt;'.  Set the layer blending mode to "Hard Light" to let the image show through&lt;br /&gt;8) Sets up the file and its attributes. (File menu)-&gt;File Info (Alt+Ctrl+i). Key in the information you want attached to the file.&lt;br /&gt;&lt;span style="font-size:78%;"&gt;copyright info: Some rights reserve. Attribution-NoDerivs 2.0 UK: England &amp; Wales &lt;strong style="font-weight: normal;"&gt;You are free: &lt;/strong&gt;to copy, distribute, display, and perform the work to make commercial use of the work(http://creativecommons.org/licenses/by-nd/2.0/uk/)&lt;br /&gt;&lt;/span&gt;9) Flatten the file.&lt;br /&gt;Watermark is done.&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;Task 3: Record Task 2 as a custom action&lt;br /&gt;&lt;br /&gt;&lt;/span&gt;Close all working files. Now we ready to create an watermark action. Most of the steps in this task is repeat from task 2.&lt;br /&gt;&lt;br /&gt;1) Open an new image to be worked on.&lt;br /&gt;2) Create a new action. Click the “create new action” icon in the Actions panel.&lt;br /&gt;3) Name this Action “watermark lanscape image”. As soon as you create a new Action, your&lt;br /&gt;action starts recording.&lt;br /&gt;4) Repeat task 2 all steps&lt;br /&gt;5) stop recording&lt;br /&gt;5) Save image use 'save as' from File menu. Remember(&lt;span style="font-weight: bold;"&gt;very important&lt;/span&gt;): DO NOT rename the file; and save it to the target output folder that batch process is output to. (the reason for this two points are explained here: &lt;a href="http://jingyeluo.blogspot.com/2006/10/photoshop-action-and-batch-to-resize.html#links"&gt;Using Photoshop Actions and batch command to resize images&lt;/a&gt;)&lt;br /&gt;5) Stop recording.&lt;br /&gt;6) Close working image,&lt;br /&gt;7) Open the original image. Test&amp; re-recording “watermark lanscape image” action to satifaction.&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;Task 4: Batch process all images&lt;/span&gt;&lt;br /&gt;1) In Photoshop, go to FILE --&gt; AUTOMATE --&gt; BATCH.&lt;br /&gt;In the Play section pull down "Action" and select "&lt;span style="font-weight: bold;"&gt;watermark lanscape image&lt;/span&gt;" action you created earlier.&lt;br /&gt;3) The “Source” Section. Since we did not create an “Open” Command in our Action, we need to make sure the “Override Action “Open” Commands” is NOT checked. The “Suppress file Open Options Dialog” should be checked. And the “Suppress Color Profile Warnings” should be checked.&lt;br /&gt;4) Click the “Choose” button and select the folder "&lt;span style="font-weight: bold;"&gt;source_landscape&lt;/span&gt;" you created in prep-work.&lt;br /&gt;5) The “Destination” Section. The “Destination” should be set to “Folder”. Click on the “Choose” button and select the folder you created called “&lt;span style="font-weight: bold;"&gt;output&lt;/span&gt;”. Make sure the “Override Action “Save As” command” is checked. Otherwise batch will create two identical files for each image – one named after original name (this is what action records in ‘save for web’) and the other name after the following pattern.&lt;br /&gt;6) In the “File Naming” Section. I prefer to prefix original image file name with something like ‘forWeb_’ just to differential it from original file. To do this Set the first box to ‘forWeb_’ second box to “Document Name” and the third box to “Extension”.&lt;br /&gt;7) uncheck 'Override Action "Save as" commands'&lt;br /&gt;8) Now, to process your images, just click “Ok”.&lt;br /&gt;And that’s it. (repeat this for protrait images)&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-7721808151322570346?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='related' href='http://www.ephotozine.com/techniques/viewtechnique.cfm?recid=339' title='Photoshop Action and Batch to watermark images'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/7721808151322570346'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/7721808151322570346'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2006/10/photoshop-action-and-batch-to-watermark.html' title='Photoshop Action and Batch to watermark images'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-8260199034888217471</id><published>2006-10-27T00:15:00.000+01:00</published><updated>2006-10-27T17:43:25.303+01:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='photoshop tips'/><title type='text'>Photoshop Action and Batch to resize images</title><content type='html'>&lt;span style="font-weight: bold;font-size:78%;" &gt;Jingye says: 'I am scratching my head on Photoshop tasks'. I am not a pro (digital) photographer. With busy life, &lt;/span&gt;&lt;span style="font-weight: bold;font-size:78%;" &gt; I just want to get some reasonable quality picture from my digital cameras&lt;/span&gt;&lt;span style="font-weight: bold;font-size:85%;" &gt;&lt;span style="font-size:78%;"&gt;. I took many many photos during holidays (easliy over 5Gb for two weeks in a exotic country).  I only have time to tidy them up a little bit, mostly an auto-leveling and an auto-curving. Then I will print some, upload a small size to &lt;a href="http://www.flickr.com/photos/i-fotos"&gt;flickr&lt;/a&gt;; archive a large version.&lt;br /&gt;&lt;br /&gt;Many ps tasks I have done in the pass were forgotten fast. So here I steal/rewrite from other people’s Photoshop tips/how to do something. I claim not rights of them unless stated. This is just my web notepad for myself and everyone else.’&lt;/span&gt;&lt;br /&gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="font-weight: bold;font-size:130%;" &gt;&lt;span style="font-family:verdana;"&gt;Using Photoshop Actions and batch command to resize images.&lt;/span&gt;&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;Rewrite and proved based on tsion (&lt;a href="http://www.sitepoint.com/forums/showthread.php?t=252128"&gt;http://www.sitepoint.com/forums/showthread.php?t=252128&lt;/a&gt; Apr 10, 2005, 10:38’s tutorial)&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;Objective&lt;/span&gt;: Create a custom action and use Photoshop’s batch command to process a group of images to a certain size.&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;Applicable versions&lt;/span&gt;: Photoshop CS (v8) and Photoshop v7&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;Prep work&lt;/span&gt;: Resize will based on a certain axis, i.e. width/height. To maintain a consistent size of a collection of photos, it is better to 1) group landscape and portrait photos in two source folder (i.e. source_landscape, source_portrait) 2) create two actions: e.g. ‘resize to width 800’ ‘resize to height 800’.&lt;br /&gt;Create an ‘output’ folder as well.&lt;br /&gt;&lt;br /&gt;In the following walk though we will do ‘resize to width 800’ only, same principle apples to ‘resize to height 800’.&lt;br /&gt;&lt;br /&gt;1)    Copy all landscape images you want to resize to the “source_landscape” folder.&lt;br /&gt;When you copy your images, I recommend you copy them all to the root directory in the “original” folder, don’t use any subfolders. This you’ll ensure that you have no duplicate images, or images with the same filename.&lt;br /&gt;&lt;br /&gt;Now we record custom automation action.&lt;br /&gt;&lt;br /&gt;2) In Photoshop, open an arbitrary image.&lt;br /&gt;3) Now, create a new action set. To do this, we click on the folder icon in the Actions panel. Let’s name this set “Custom”. I like to keep my custom actions in their own set, so I can find them easier later on.&lt;br /&gt;4) Next create a new action. Click the “create new action” icon in the Actions panel.&lt;br /&gt;5) Name this Action “resize to width 800” As soon as you create a new Action, your action starts recording.&lt;br /&gt;6) To resize the image: Go to IMAGE --&gt; RESIZE IMAGE. This will open the “Image Size” dialog box. Now let’s change the width of our image to 800 pixels wide. Then click “OK”.&lt;br /&gt;7) Now immediately after you click “OK”. Go to FILE --&gt; SAVE FOR WEB. Set your jpg parameters how you normally would and click save.&lt;br /&gt;Due to a bug in cs, there are two things described here must be follow:&lt;br /&gt;7.1 Make sure you save this file in the “output” folder that we created in prep work.&lt;br /&gt;7.2 DO NOT rename the file, just save it as it is. Otherwise you will get ‘Replace Files’ message window in batch process later for each image. (more below)&lt;br /&gt;&lt;br /&gt;8) Click the “Stop recording” icon in the Actions panel. Our new Action is complete, and ready to use.&lt;br /&gt;Now we are ready to process our images.&lt;br /&gt;&lt;br /&gt;9) Go to “output” folder and delete the image you saved there when you created your action. This is just so it doesn’t get mixed in with the images you’re processing.&lt;br /&gt;&lt;br /&gt;10) In Photoshop, go to FILE --&gt; AUTOMATE --&gt; BATCH.&lt;br /&gt;&lt;br /&gt;11) The “Play” section. Change your set to “Custom”. And your Action to ““resize to width 800” this sets the Action you created earlier.&lt;br /&gt;&lt;br /&gt;12) The “Source” Section. Since we did not create an “Open” Command in our Action, we need to make sure the “Override Action “Open” Commands” is NOT checked. The “Include Subfolders” option doesn’t matter. The “Suppress file Open Options Dialog” should be checked. And the “Suppress Color Profile Warnings” should be checked.&lt;br /&gt;&lt;br /&gt;13) Click the “Choose” button and select the folder "&lt;span style="font-weight: bold;"&gt;source_landscape&lt;/span&gt;" you created in prep-work.&lt;br /&gt;&lt;br /&gt;14)  The “Destination” Section. The “Destination” should be set to “Folder”. Click on the “Choose” button and select the folder you created called “&lt;span style="font-weight: bold;"&gt;output&lt;/span&gt;”. Make sure the “Override Action “Save As” command” is checked. Otherwise batch will create two identical files for each image – one named after original name (this is what action records in ‘save for web’) and the other name after the following pattern.&lt;br /&gt;&lt;br /&gt;15) In the “File Naming” Section. I prefer to prefix original image file name with something like ‘forWeb_’ just to differential it from original file. To do this Set the first box to ‘forWeb_’ second box to “Document Name” and the third box to “Extension”.&lt;br /&gt;&lt;br /&gt;Now, to process your images, just click “Ok”.&lt;br /&gt;And that’s it.&lt;br /&gt;&lt;br /&gt;Question 1: When I run the batch command, PCS brings up the replace image dialogue asking me is I want to replace the previously saved image, which obviously I don't.&lt;br /&gt;What am I missing?&lt;br /&gt;&lt;br /&gt;Answer: First, the output folder in ‘resize to width 800’ action must be identical to what it is set in batch process output folder.&lt;br /&gt;Second, Do not rename the file in recording the action, this seemed like confused the batch process.&lt;br /&gt;&lt;br /&gt;Question 2: 'm trying to batch process ..alot of images...but everytime i run the batch, the picture quality appears after each image, asking me to save at what size. This is alot to go thorugh when i have thousands of pics, is there a way around this? So far from what i've seen, the answer is no.&lt;br /&gt;&lt;br /&gt;Answer: use ‘Save for web’, not ‘save as’&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-8260199034888217471?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='related' href='http://www.sitepoint.com/forums/showthread.php?t=252128' title='Photoshop Action and Batch to resize images'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/8260199034888217471'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/8260199034888217471'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2006/10/photoshop-action-and-batch-to-resize.html' title='Photoshop Action and Batch to resize images'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-2217017486048249244</id><published>2006-10-23T16:11:00.000+01:00</published><updated>2006-10-24T08:48:11.749+01:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='tdd'/><title type='text'>Strong Typing vs. Strong Testing</title><content type='html'>[Blog on Blog]&lt;br /&gt;&lt;br /&gt;&lt;span style=";font-family:Verdana;color:black;"  &gt;... without a full set of unit tests (at the very least), you can't guarantee the correctness of a program. To claim that the strong, static type checking constraints in C++, Java, or C# will prevent you from writing broken programs is clearly an illusion (you know this from personal experience). In fact, what we need is &lt;o:p&gt;&lt;/o:p&gt;&lt;/span&gt;  &lt;p class="MsoNormal"&gt;&lt;b&gt;&lt;span style=";font-family:Verdana;color:black;"  &gt;Strong testing, not strong typing. &lt;/span&gt;&lt;/b&gt;&lt;span style=";font-family:Verdana;color:black;"  &gt;&lt;o:p&gt;&lt;/o:p&gt;&lt;/span&gt;&lt;/p&gt;  points to note:&lt;br /&gt;&lt;br /&gt;&lt;ol style="margin-top: 0cm;" start="1" type="1"&gt;&lt;li class="MsoNormal" style=""&gt;A      very concise code sample comparing strong type and weak type language,      where weak type loose the semantic on checking variable type – it works as      long as it implements the method expected.&lt;/li&gt;&lt;li class="MsoNormal" style=""&gt;unit      test is an extension to complier&lt;/li&gt;&lt;/ol&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-2217017486048249244?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='related' href='http://www.mindview.net/WebLog/log-0025' title='Strong Typing vs. Strong Testing'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/2217017486048249244'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/2217017486048249244'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2006/10/strong-typing-vs-strong-testing.html' title='Strong Typing vs. Strong Testing'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-8651411255626110513</id><published>2006-10-03T11:23:00.000+01:00</published><updated>2006-10-03T11:29:43.003+01:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='asp.net'/><category scheme='http://www.blogger.com/atom/ns#' term='mono'/><title type='text'>mono XslTransform vs .net XslTransform observation</title><content type='html'>Although by and large mono is the reincarnation of .net for the  poor, there are subtle differences between them. Here is what I found on Xsl  Transformation. Mono XML interprets xsl:last() function in a significant  different way to native .net. XML.&lt;br /&gt;&lt;div id="mb_0"&gt;&lt;br /&gt;Using the same xml style sheet with a  few debug trace: p – xsl:position(); l – xsl:last; c-xsl:count()&lt;br /&gt;Mono  rendering:&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://photos1.blogger.com/blogger2/3778/742/1600/xslt_lastFunc_mono.gif"&gt;&lt;img style="margin: 0px auto 10px; display: block; text-align: center; cursor: pointer;" src="http://photos1.blogger.com/blogger2/3778/742/400/xslt_lastFunc_mono.png" alt="" border="0" /&gt;&lt;/a&gt;&lt;br /&gt;Native .Net rendering:&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://photos1.blogger.com/blogger2/3778/742/1600/xslt_lastFunc_net.gif"&gt;&lt;img style="margin: 0px auto 10px; display: block; text-align: center; cursor: pointer;" src="http://photos1.blogger.com/blogger2/3778/742/400/xslt_lastFunc_net.png" alt="" border="0" /&gt;&lt;/a&gt;&lt;br /&gt;And the source code:&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://photos1.blogger.com/blogger2/3778/742/1600/xslt_lastFunc_source.gif"&gt;&lt;img style="margin: 0px auto 10px; display: block; text-align: center; cursor: pointer;" src="http://photos1.blogger.com/blogger2/3778/742/400/xslt_lastFunc_source.gif" alt="" border="0" /&gt;&lt;/a&gt;We  also found the insignificant whitespaces in the two versions are placed  differently.&lt;br /&gt;&lt;br /&gt;We are able to spot these difference in a consistent,  repeatable and fully automated way by writing &lt;a onclick="return top.js.OpenExtLink(window,event,this)" href="http://jingyeluo.blogspot.com/2006/08/tdd-web-controls-dev-life-cycle.html" target="_blank"&gt;Ruby+Watier&lt;/a&gt; scripts before writing  any code. The test script  fully emulates an IE browser object. It instantiates an browser window and  issues http request. We can then either assert the html source character by  character or more semantically and interactively,  do things like @ie(:id,  "myLink").click&lt;br /&gt;&lt;/div&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-8651411255626110513?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/8651411255626110513'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/8651411255626110513'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2006/10/mono-xsltransform-vs-net-xsltransform.html' title='mono XslTransform vs .net XslTransform observation'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-8350468882091890742</id><published>2006-09-15T08:45:00.000+01:00</published><updated>2006-09-15T08:47:57.553+01:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='xml'/><title type='text'>update/delete/insert nodes to an xml document</title><content type='html'>&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://photos1.blogger.com/blogger2/3778/742/1600/sample.jpg"&gt;&lt;img style="margin: 0px auto 10px; display: block; text-align: center; cursor: pointer;" src="http://photos1.blogger.com/blogger2/3778/742/400/sample.jpg" alt="" border="0" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;div&gt;Load an xml document to memory. Nevigate the DOM object, using xpath to  query nodes. To update the node: create an new one, and replace the existing  one.&lt;/div&gt; &lt;div&gt;Default namespace in xml doc still needs to declare in namespace mamager-  and use in the xpath query. Although it is not present in the xml data:&lt;/div&gt; &lt;div&gt; &lt;/div&gt; &lt;div&gt;Sample Data&lt;br /&gt;&lt;br /&gt;&lt;/div&gt; &lt;div&gt; &lt;/div&gt; &lt;div&gt;C# Code to do this:&lt;br /&gt;&lt;span style="font-size:85%;"&gt;&lt;span style="font-family: courier new;"&gt;        private void SetTestData(int index, int itemsPerPage, int totalResults)&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family: courier new;"&gt;        {&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family: courier new;"&gt;            XmlTextReader reader = new XmlTextReader("..\\TestData_V1.xml");&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family: courier new;"&gt;            XmlDocument doc = new XmlDocument(); &lt;/span&gt;&lt;br /&gt;&lt;span style="font-family: courier new;"&gt;            doc.Load(reader);&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family: courier new;"&gt;            reader.Close();&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-family: courier new;"&gt;            string osUri = "http://a9.com/-/spec/opensearch/1.1/";&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-family: courier new;"&gt;            XmlNamespaceManager nsMgr = new XmlNamespaceManager(doc.NameTable);&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family: courier new;"&gt;            nsMgr.AddNamespace("os", osUri);&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family: courier new;"&gt;            nsMgr.AddNamespace("rdf", "http://www.w3.org/1999/02/22-rdf-syntax-ns#");&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family: courier new;"&gt;            nsMgr.AddNamespace("dc", "http://purl.org/dc/elements/1.1/");&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family: courier new;"&gt;            nsMgr.AddNamespace("rss", "http://purl.org/rss/1.0/");&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-family: courier new;"&gt;            XmlNode oStartIndex, oItermsPerPage, oTotalResults;&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family: courier new;"&gt;            XmlElement root = doc.DocumentElement;&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-family: courier new;"&gt;            oStartIndex = root.SelectSingleNode("/rdf:RDF/rss:channel/os:totalResults", nsMgr);&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family: courier new;"&gt;            oItermsPerPage = root.SelectSingleNode("/rdf:RDF/rss:channel/os:itemsPerPage", nsMgr);&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family: courier new;"&gt;            oTotalResults = root.SelectSingleNode("/rdf:RDF/rss:channel/os:startIndex", nsMgr);&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-family: courier new;"&gt;            XmlElement nStartIndex = doc.CreateElement("os", "startIndex", osUri);&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family: courier new;"&gt;            XmlElement nItermsPerPage = doc.CreateElement("os", "itemsPerPage", osUri);&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family: courier new;"&gt;            XmlElement nTotalResults = doc.CreateElement("os", "totalResults", osUri);&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-family: courier new;"&gt;            nStartIndex.InnerXml = index.ToString();&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family: courier new;"&gt;            nItermsPerPage.InnerXml = itemsPerPage.ToString();&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family: courier new;"&gt;            nTotalResults.InnerXml = totalResults.ToString();&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-family: courier new;"&gt;            root.SelectSingleNode("/rdf:RDF/rss:channel", nsMgr).ReplaceChild(nStartIndex, oStartIndex);&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family: courier new;"&gt;            root.SelectSingleNode("/rdf:RDF/rss:channel", nsMgr).ReplaceChild(nItermsPerPage, oItermsPerPage);&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family: courier new;"&gt;            root.SelectSingleNode("/rdf:RDF/rss:channel", nsMgr).ReplaceChild(nTotalResults, oTotalResults);&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-family: courier new;"&gt;            doc.Save("..\\tempTestData.xml");&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family: courier new;"&gt;        }&lt;/span&gt;&lt;/span&gt;&lt;br /&gt;&lt;/div&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-8350468882091890742?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/8350468882091890742'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/8350468882091890742'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2006/09/updatedeleteinsert-nodes-to-xml.html' title='update/delete/insert nodes to an xml document'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-1857886258938673060</id><published>2006-09-02T11:16:00.000+01:00</published><updated>2006-09-02T11:17:03.941+01:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='asp.net'/><title type='text'>The ASP.NET Page Object Model</title><content type='html'>&lt;p&gt;Revisit and take away from Dino Esposito's classic article &lt;a href="http://msdn.microsoft.com/library/default.asp?url=/library/en-us/dnaspp/html/aspnet-pageobjectmodel.asp"&gt;The ASP.NET Page Object Model&lt;/a&gt;&lt;/p&gt;&lt;p style="font-weight: bold;"&gt;Code Behind&lt;/p&gt;&lt;p&gt;&lt;span style="font-style: italic;"&gt;The code of a page is &lt;span style="font-weight: bold;"&gt;the set of event handlers and helper methods&lt;/span&gt; that actually create the behavior of the page. This code can be defined inline using the &lt;/span&gt;&lt;span style="font-style: italic;"&gt; tag or placed in an external class—the code-behind class.&lt;/span&gt;&lt;/p&gt;&lt;ol&gt;&lt;li&gt;Think it this way make it easier to break away sequnential mentally on reading/writing code.&lt;/li&gt;&lt;li&gt;Code behind is totally optional.&lt;br /&gt;&lt;/li&gt;&lt;ol&gt;&lt;li&gt;You can have 'orphan' aspx page derived from web.UI.Page directly. In situations, say that you are testing good and feel of a web control&lt;/li&gt;&lt;li&gt;You can have all aspx derived from a common code-behind class&lt;br /&gt;&lt;/li&gt;&lt;/ol&gt;&lt;/ol&gt;&lt;p&gt;&lt;span style="font-weight: bold;"&gt;AutoEventWireup&lt;/span&gt;&lt;/p&gt;&lt;p&gt;VSNET IDE wizard generates boiler-plate aspx contains @page like this&lt;/p&gt;&lt;p  style="font-family:courier new;"&gt;&lt;span style="font-size:85%;"&gt;&amp;lt;%@ Page language="c#" Codebehind="MyPage.aspx.cs" AutoEventWireup="false" Inherits="MyNameSpace.MyPage" %&amp;gt;&lt;/span&gt;&lt;/p&gt;&lt;p&gt;For backward compatibility with the earlier VB programming style, ASP.NET also supports a form of implicit event hooking. By default, the page tries to match special method names with events; if a match is found, the method is considered a handler for the event. ASP.NET provides special recognition of six method names. They are &lt;b&gt;Page_Init&lt;/b&gt; &lt;b&gt;Page_Load&lt;/b&gt;, &lt;b&gt;Page_DataBind&lt;/b&gt;, &lt;b&gt;Page_PreRender&lt;/b&gt;, and &lt;b&gt;Page_Unload&lt;/b&gt;. These methods are treated as handlers for the corresponding events exposed by the &lt;b&gt;Page&lt;/b&gt; class. The HTTP run time will automatically bind these methods to page events saving developers from having to write the necessary glue code. For example, the method named &lt;b&gt;Page_Load&lt;/b&gt; is wired to the page's &lt;b&gt;Load&lt;/b&gt; event as if the following code was written.&lt;/p&gt;  &lt;pre class="code"&gt;this.Load += new EventHandler(this.Page_Load);&lt;br /&gt;&lt;/pre&gt;  &lt;p&gt;The automatic recognition of special names is a behavior under the control of the &lt;b&gt;AutoEventWireup&lt;/b&gt; attribute of the &lt;b&gt;@Page&lt;/b&gt; directive. If the attribute is set to false, any applications that wish to handle an event need to connect explicitly to the page event. Pages that don't use automatic event wire-up will get a slight performance boost by not having to do the extra work of matching names and events. Although VSNET creates aspx with the &lt;b&gt;AutoEventWireup&lt;/b&gt; attribute disabled, the default setting for the attribute is &lt;span style="font-weight: bold;"&gt;true&lt;/span&gt;, meaning that methods such as &lt;b&gt;Page_Load &lt;/b&gt;are recognized and bound to the associated event.&lt;br /&gt;&lt;/p&gt;&lt;p&gt;You should always explicitly register an appropriate handler instead of relying on AutoEventWireup.&lt;/p&gt;&lt;p&gt;Another interesting experitment. set AutoEventWireup="true" and also keep the following line in the InitializeComponent of code-behind. Put a Response.Write to it. It is called twice!&lt;/p&gt;&lt;p&gt;&lt;span style="font-size:85%;"&gt;&lt;span style="font-family:courier new;"&gt; this.Load += new System.EventHandler(this.Page_Load);&lt;/span&gt;&lt;/span&gt;&lt;br /&gt;&lt;/p&gt;&lt;span style="font-weight: bold;"&gt;The Page Lifecycle&lt;br /&gt;&lt;br /&gt;&lt;/span&gt;&lt;table class="data"&gt;&lt;tbody&gt;&lt;tr valign="top"&gt;&lt;th class="data" align="left" width="34%"&gt;Stage&lt;/th&gt; &lt;th class="data" align="left" width="18%"&gt;Page Event&lt;/th&gt; &lt;th class="data" align="left" width="48%"&gt;Overridable method&lt;/th&gt; &lt;/tr&gt;  &lt;tr valign="top"&gt; &lt;td class="data" width="34%"&gt;&lt;ul&gt;&lt;li&gt;&lt;span style="font-size:85%;"&gt;Page initialization&lt;/span&gt;&lt;/li&gt;&lt;/ul&gt;&lt;/td&gt; &lt;td class="data" width="18%"&gt;&lt;span style="font-size:85%;"&gt;&lt;b&gt;Init&lt;br /&gt;&lt;br /&gt;&lt;/b&gt;&lt;/span&gt;&lt;/td&gt; &lt;td class="data" width="48%"&gt;&lt;span style="font-size:85%;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;/td&gt; &lt;/tr&gt;  &lt;tr valign="top"&gt; &lt;td class="data" width="34%"&gt;&lt;ul&gt;&lt;li&gt;&lt;span style="font-size:85%;"&gt;View state loading&lt;/span&gt;&lt;/li&gt;&lt;/ul&gt;&lt;/td&gt; &lt;td class="data" width="18%"&gt;&lt;span style="font-size:85%;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;/td&gt; &lt;td class="data" width="48%"&gt;&lt;span style="font-size:85%;"&gt;&lt;b&gt;LoadViewState&lt;/b&gt; Restores view-state information from a previous page request that was saved by the SaveViewState method&lt;br /&gt;&lt;br /&gt;&lt;/span&gt;&lt;/td&gt; &lt;/tr&gt;  &lt;tr valign="top"&gt; &lt;td class="data" width="34%"&gt;&lt;ul&gt;&lt;li&gt;&lt;span style="font-size:85%;"&gt;Postback data processing&lt;/span&gt;&lt;/li&gt;&lt;/ul&gt;&lt;/td&gt; &lt;td class="data" width="18%"&gt;&lt;span style="font-size:85%;"&gt;(implicitly by Page base class -ProcessPostData (private))&lt;br /&gt;&lt;/span&gt;&lt;/td&gt; &lt;td class="data" width="48%"&gt;&lt;span style="font-size:85%;"&gt;Call to &lt;b&gt;LoadPostData&lt;/b&gt; methods in the controls tree that implements the &lt;b&gt;System.Web.UI.IPostBackDataHandler&lt;/b&gt;&lt;br /&gt;&lt;br /&gt;&lt;/span&gt; interface (e.g. TextBox)&lt;/td&gt; &lt;/tr&gt;  &lt;tr valign="top"&gt; &lt;td class="data" width="34%"&gt;&lt;ul&gt;&lt;li&gt;&lt;span style="font-size:85%;"&gt;Page loading&lt;/span&gt;&lt;/li&gt;&lt;/ul&gt;&lt;/td&gt; &lt;td class="data" width="18%"&gt;&lt;span style="font-size:85%;"&gt;&lt;b&gt;Load&lt;/b&gt;&lt;/span&gt;&lt;/td&gt; &lt;td class="data" width="48%"&gt;&lt;span style="font-size:85%;"&gt;&lt;br /&gt;&lt;br /&gt;&lt;/span&gt;&lt;/td&gt; &lt;/tr&gt;  &lt;tr valign="top"&gt; &lt;td class="data" width="34%"&gt;&lt;ul&gt;&lt;li&gt;&lt;span style="font-size:85%;"&gt;Postback change notification&lt;/span&gt;&lt;/li&gt;&lt;/ul&gt;&lt;/td&gt; &lt;td class="data" width="18%"&gt;&lt;span style="font-size:85%;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;/td&gt; &lt;td class="data" width="48%"&gt;&lt;span style="font-size:85%;"&gt;&lt;b&gt;RaisePostDataChangedEvent&lt;/b&gt; method in any control that implements the &lt;b&gt;IPostBackDataHandler&lt;/b&gt; interface&lt;br /&gt;&lt;br /&gt;&lt;/span&gt;&lt;/td&gt; &lt;/tr&gt;  &lt;tr valign="top"&gt; &lt;td class="data" width="34%"&gt;&lt;ul&gt;&lt;li&gt;&lt;span style="font-size:85%;"&gt;Postback event handling&lt;/span&gt;&lt;/li&gt;&lt;/ul&gt;&lt;/td&gt; &lt;td class="data" width="18%"&gt;&lt;span style="font-size:85%;"&gt;Any postback event defined by controls&lt;/span&gt;&lt;/td&gt; &lt;td class="data" width="48%"&gt;&lt;span style="font-size:85%;"&gt;&lt;b&gt;RaisePostBackEvent&lt;/b&gt; method in any control that implements the &lt;b&gt;IPostBackEventHandler&lt;/b&gt; interface&lt;br /&gt;&lt;br /&gt;&lt;/span&gt; &lt;/td&gt; &lt;/tr&gt;  &lt;tr valign="top"&gt; &lt;td class="data" width="34%"&gt;&lt;ul&gt;&lt;li&gt;&lt;span style="font-size:85%;"&gt;Page pre-rendering phase&lt;/span&gt;&lt;/li&gt;&lt;/ul&gt;&lt;/td&gt; &lt;td class="data" width="18%"&gt;&lt;span style="font-size:85%;"&gt;&lt;b&gt;PreRender&lt;/b&gt;&lt;/span&gt;&lt;/td&gt; &lt;td class="data" width="48%"&gt;&lt;span style="font-size:85%;"&gt;&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;/span&gt;&lt;/td&gt; &lt;/tr&gt;  &lt;tr valign="top"&gt; &lt;td class="data" width="34%"&gt;&lt;ul&gt;&lt;li&gt;&lt;span style="font-size:85%;"&gt;View state saving&lt;/span&gt;&lt;/li&gt;&lt;/ul&gt;&lt;/td&gt; &lt;td class="data" width="18%"&gt;&lt;span style="font-size:85%;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;/td&gt; &lt;td class="data" width="48%"&gt;&lt;span style="font-size:85%;"&gt;&lt;b&gt;SaveViewState&lt;br /&gt;&lt;br /&gt;&lt;/b&gt;&lt;/span&gt;&lt;/td&gt; &lt;/tr&gt;  &lt;tr valign="top"&gt; &lt;td class="data" width="34%"&gt;&lt;ul&gt;&lt;li&gt;&lt;span style="font-size:85%;"&gt;Page rendering&lt;/span&gt;&lt;/li&gt;&lt;/ul&gt;&lt;/td&gt; &lt;td class="data" width="18%"&gt;&lt;span style="font-size:85%;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;/td&gt; &lt;td class="data" width="48%"&gt;&lt;span style="font-size:85%;"&gt;&lt;b&gt;Render&lt;br /&gt;&lt;br /&gt;&lt;/b&gt;&lt;/span&gt;&lt;/td&gt; &lt;/tr&gt;  &lt;tr valign="top"&gt; &lt;td class="data" width="34%"&gt;&lt;ul&gt;&lt;li&gt;&lt;span style="font-size:85%;"&gt;Page unloading&lt;/span&gt;&lt;/li&gt;&lt;/ul&gt;&lt;/td&gt; &lt;td class="data" width="18%"&gt;&lt;span style="font-size:85%;"&gt;&lt;b&gt;Unload&lt;/b&gt;&lt;/span&gt;&lt;/td&gt; &lt;td class="data" width="48%"&gt;&lt;br /&gt;&lt;/td&gt;&lt;/tr&gt;&lt;/tbody&gt;&lt;/table&gt;&lt;p&gt;The ProcessPostData is a private method implemeted at Page class which contains code like this:&lt;/p&gt;&lt;p&gt;&lt;span style="font-size:85%;"&gt;&lt;span style="font-family:courier new;"&gt;IPostBackDataHandler handler1 = (IPostBackDataHandler) control1;&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;if (handler1.LoadPostData(text1, this._requestValueCollection))&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;{&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;    this._changedPostDataConsumers.Add(handler1);&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;}&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;if (this._controlsRequiringPostBack != null)&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;{&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;    this._controlsRequiringPostBack.Remove(text1);&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;}&lt;/span&gt;&lt;br /&gt;&lt;/span&gt;&lt;br /&gt;A simple page to demo this cycle: &lt;a href="http://beta.blogger.com/comingup.nemonova.com/PageLifeCycle.zip"&gt;PageLifeCycle.zip&lt;/a&gt; (contains PageLifeCycle.cs and .aspx, unzip and add them to a web proj. to see it in action)&lt;br /&gt;&lt;/p&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-1857886258938673060?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='related' href='http://msdn.microsoft.com/library/default.asp?url=/library/en-us/dnaspp/html/aspnet-pageobjectmodel.asp' title='The ASP.NET Page Object Model'/><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/1857886258938673060/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=1857886258938673060' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/1857886258938673060'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/1857886258938673060'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2006/09/aspnet-page-object-model.html' title='The ASP.NET Page Object Model'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-1373272299522328813</id><published>2006-08-31T21:26:00.000+01:00</published><updated>2006-08-31T21:32:44.742+01:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='asp.net'/><category scheme='http://www.blogger.com/atom/ns#' term='tdd'/><title type='text'>TDD web controls dev life cycle</title><content type='html'>&lt;span style="font-style: italic;"&gt;An entire upside down experience to help coder focus on deliver 'good enough' requirements&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;In &lt;span style="font-weight: bold;"&gt;summary&lt;/span&gt; this dev pattern is&lt;br /&gt;&lt;br /&gt;1. decide deliverables - the rendered html as browser user sees. (step 1, 2)&lt;br /&gt;2. write ruby script to test the html (in fact it is reversed test the test script) (step 3)&lt;br /&gt;3. act as web designer to use the web control to build a test page (of course, the web control is not existed yet) (step 4)&lt;br /&gt;4. Implment web control (step 5)&lt;br /&gt;5. test the web control (step 6-7)&lt;br /&gt;6. change loop&lt;br /&gt;&lt;br /&gt;A well designed website should be broken into three domains:&lt;br /&gt;1) Reusable Web controls which render plain html&lt;br /&gt;2) bare bone website composed of web controls. Pages are served as control containers and responsible for managing navigation, user experience. It should contains no inline css but class/id/name that allows UI designer change the 'skin' without touching the website, not even a downtime.&lt;br /&gt;3) CSS&lt;br /&gt;&lt;br /&gt;Here is the &lt;span style="font-weight: bold;"&gt;Test Driven Development Cycle&lt;/span&gt;&lt;br /&gt;1. Agree with UI designer on html template. the static html prototype is the 'contract'.&lt;br /&gt;&lt;br /&gt;2. break down the template into componentised controls that will be generated with user/custom controls. Save the html corresponding to the control to a new html e.g. ~\gallery\searchbox.html&lt;br /&gt;&lt;span style="font-size:85%;"&gt;&lt;span style="font-family:courier new;"&gt;&amp;lt;html&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;    &amp;lt;body&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;        &amp;lt;!--search box--&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;        &amp;lt;div id="PARENTDIV" name="PARENTDIV" class="TestGlobalStyleClass"&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;            &amp;lt;label id="PARENTDIV.MessageLabel" name="PARENTDIV.MessageLabel"&amp;gt;TestMessageLabelText&amp;lt;/label&amp;gt;&amp;lt;br&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;            &amp;lt;input type="text" id="PARENTDIV.SearchTerm" name="PARENTDIV.SearchTerm" class="SearchTermClass" size="100" maxlength="100"&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;            &amp;lt;a href="http://test.webcontrols.com" id="PARENTDIV.AdvLink" name="PARENTDIV.AdvLink"&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;                title="Test ToolTip" class="AdvLinkClass"&amp;gt;Test Link Text&amp;lt;/a&amp;gt; &lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;            &amp;lt;!--search box close--&amp;gt;&amp;lt;/div&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;    &amp;lt;/body&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;&amp;lt;/html&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;/span&gt;&lt;br /&gt;3. Write an Ruby script 'SearchBoxTestFixture.rb' to test this template. This is to validate our test case is sounds.&lt;br /&gt;&lt;br /&gt;&lt;span style="font-size:85%;"&gt;&lt;span style="font-family:courier new;"&gt;require 'watir'&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;require 'test/unit'&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;require 'test/unit/assertions'&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;include Watir&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;class SearchBoxTestFixture &lt;&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;    def setup&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;        localHostXSP = "http://127.0.0.1"&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;        localHostIIS = "http://localhost/Talis.Web.Cenote.WebControls.Test"        &lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;        @staticTemplate = 'http://localhost/Talis.Web.Cenote.WebControls.Test/static/searchbox.html'&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;        remoteHost = "http://talis.com";&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;        @testSite = localHostIIS&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;        @ie = IE.new&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;    end&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;    &lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;    def teardown&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;        @ie.close&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;    end&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;    &lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;    def test_allHtmlElementsExist&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;        # page = "SearchBoxTest.aspx"&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;        # @ie.goto(@testSite+'/'+page)&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;        &lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;        # test static html template&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;        @ie.goto(@staticTemplate)&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;        &lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;        assert_equal(1, @ie.divs.length, 'Expecting only one div')&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;        assert(@ie.div(:id, /PARENTDIV/).exists?, "Expecting div id 'PARENTDIV'")&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;        assert(@ie.div(:name, /PARENTDIV/).exists?, "Expecting div name 'PARENTDIV'")&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;        &lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;        #assert message label&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;        assert_equal(1, @ie.labels.length, 'Expecting only one lable box')&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;        assert(@ie.label(:id, /PARENTDIV.MessageLabel/).exists?, "Expecting label id 'PARENTDIV.MessageLabel'")&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;        assert(@ie.label(:name, /PARENTDIV.MessageLabel/).exists?, "Expecting label name 'PARENTDIV.MessageLabel'" )&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;        assert('TestMessageLabelText', @ie.label(:id, "PARENTDIV.MessageLabel").innerText)&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;        &lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;        #assert input box&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;        assert_equal(1, @ie.text_fields.length, 'Expecting only one input box')&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;        assert(@ie.div(:id, /PARENTDIV/).text_field(:id, 'PARENTDIV.SearchTerm').enabled?, "Expecting textbox id 'PARENTDIV.SearchTerm'"  )&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;        assert(@ie.text_field(:name, 'PARENTDIV.SearchTerm').exists?, "Expecting textbox name'PARENTDIV.SearchTerm' textbox element")&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;        assert_equal(100, @ie.text_field(:id, 'PARENTDIV.SearchTerm').size(), "Expecting textbox size 100")&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;        assert_equal(100, @ie.text_field(:id, 'PARENTDIV.SearchTerm').maxLength(), "Expecting textbox maxLength 100")&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;        &lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;        #assert link&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;        assert_equal(1, @ie.links.length, 'Expecting only one link')&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;        assert(@ie.link(:id, 'PARENTDIV.AdvLink').exists?, "Expecting link id 'PARENTDIV.AdvLink'" )&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;        assert(@ie.link(:name, /PARENTDIV.AdvLink/).exists?, "Expecting link name 'PARENTDIV.AdvLink'" )&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;        assert_equal('http://test.webcontrols.com/', @ie.link(:name, /PARENTDIV.AdvLink/).href, "Expecting link url 'http://test.webcontrols.com'" )&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;        assert(@ie.link(:title, 'Test ToolTip').exists?, "Expecting link title (tool tip) 'Test ToolTip'" )&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;        assert_equal('Test Link Text', @ie.link(:id, 'PARENTDIV.AdvLink').innerText, "Expecting link text 'Test Link Text'" )&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;    end&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;end&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;/span&gt;4. write SearchBoxTest.aspx that intend to render as to searchbox.html. Ours contains this:&lt;br /&gt;&lt;span style="font-size:85%;"&gt;&lt;span style="font-family:courier new;"&gt;        &amp;lt;My:SearchBox &lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;            ID="PARENTDIV"&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;            Class="TestGlobalStyleClass"&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;            MessageLabel_Text="TestMessageLabelText"&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;            MessageLabel_Class="TestMessageLabelClass"&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;            SearchTerm_Class="SearchTermClass"&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;            SearchTerm_Size="100"&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;            AdvLink_Class="AdvLinkClass"&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;            AdvLink_Tooltip="Test ToolTip"&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;            AdvLink_InnerText="Test Link Text"&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;            Runat="server"&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;        /&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;/span&gt;&lt;br /&gt;5. Implement the custom web control: SearchBox.cs&lt;br /&gt;&lt;br /&gt;6. If haven't done so, write nUnit Testfixture to hook* ruby script into your test dll. So all tests will feedback as red/green light&lt;br /&gt;&lt;br /&gt;7. Modify SearchBoxTestFixture.rb to target SearchBoxTest.rb.&lt;br /&gt;&lt;br /&gt;Contract changed, start from 1. again&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;Notes:&lt;/span&gt;&lt;br /&gt;1. You need to install&lt;span style="font-size:85%;"&gt;&lt;span style="font-style: normal; font-variant: normal; font-weight: normal; line-height: normal; font-size-adjust: none; font-stretch: normal;"&gt;          &lt;/span&gt;&lt;/span&gt;&lt;span style="font-size:85%;"&gt;&lt;a href="http://rubyforge.org/projects/rubyinstaller/"&gt;Ruby&lt;/a&gt;&lt;/span&gt; &lt;span style="font-size:85%;"&gt;&lt;span style="font-style: normal; font-variant: normal; font-weight: normal; line-height: normal; font-size-adjust: none; font-stretch: normal;"&gt;          &lt;/span&gt;&lt;/span&gt;&lt;span style="font-size:85%;"&gt;&lt;a href="http://rubyforge.org/frs/?group_id=104"&gt;WATIR&lt;/a&gt; &lt;/span&gt;&lt;br /&gt;2. Travis &lt;span style="font-size:85%;"&gt;Illig has this fatastic&lt;/span&gt; RubyTestExecutor integrates ruby and watir test scripts into nUnit test framework. Check his paper &lt;span style="font-size:85%;"&gt;&lt;/span&gt;&lt;a href="http://www.codeproject.com/cpnet/RubyTestExecutor.asp"&gt;Integrated ASP.NET Web Application Testing with NUnit, Ruby, and Watir&lt;/a&gt; on code project.&lt;/span&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-1373272299522328813?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/1373272299522328813/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=1373272299522328813' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/1373272299522328813'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/1373272299522328813'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2006/08/tdd-web-controls-dev-life-cycle.html' title='TDD web controls dev life cycle'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-115697877599595408</id><published>2006-08-30T23:59:00.000+01:00</published><updated>2006-08-31T00:06:17.440+01:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='asp.net'/><category scheme='http://www.blogger.com/atom/ns#' term='mono'/><category scheme='http://www.blogger.com/atom/ns#' term='iis'/><title type='text'>Mono is not an adaptive asp.net web rendering engine</title><content type='html'>&lt;div&gt;Scott Mitchell writes in &lt;a href="http://aspnet.4guysfromrolla.com/articles/050504-1.aspx"&gt;ASP.NET.4GuysFromRolla.com: A Look at ASP.NET's Adaptive Rendering&lt;/a&gt;: IIS &lt;a href="http://asp.net/"&gt;ASP.NET&lt;/a&gt; renders web controls by first detect the user-agnet type, for this reason,  &lt;a href="http://asp.net/"&gt;ASP.NET&lt;/a&gt; Web controls are called &lt;strong&gt;adaptive&lt;/strong&gt;. By default it renders HTML 3.2-compliant markup using &lt;span style="font-family:Courier New;"&gt;&lt;strong&gt;tagwriter=System.Web.UI.Html32TextWriter.&lt;/strong&gt;  &lt;/span&gt;&lt;span style="font-family:Arial;"&gt;For&lt;br /&gt;HTML 4.0-compliant agents (Mozilla/4.0 and above, e.g. MSIE6) it uses &lt;/span&gt;&lt;span style="font-family:courier new,monospace;"&gt;&lt;strong&gt;tagwriter=System.Web.UI.HtmlTextWriter. &lt;/strong&gt;&lt;/span&gt;IIS does so by having a regex check for browser User-Agent. However, the default implementation doesn't address FireFox  0.8 and above, which is Mozilla/5.0 and HTML 4.0-compliant.&lt;/div&gt; &lt;div&gt; &lt;/div&gt; &lt;div&gt;Here we will check the adaptive rendering issue around Mono1.x ASPNET instead of IIS.&lt;/div&gt; &lt;div&gt; &lt;p&gt;Default behaviour&lt;br /&gt;1. Test rendering by Mono XSP web server.&lt;br /&gt;On MSIE 6.0:  &lt;span style="font-family:courier new,monospace;"&gt;tagwriter=System.Web.UI.&lt;strong&gt;HtmlTextWriter&lt;/strong&gt;&lt;/span&gt;&lt;br /&gt;evidence: System.Web.UI.WebControls.WebControl  is rendered as &amp;lt;div&amp;gt;&lt;br /&gt;On FireFox 1.5: &lt;span style="font-family:courier new,monospace;"&gt;tagwriter=System.Web.UI.&lt;strong&gt;HtmlTextWriter&lt;/strong&gt;&lt;br /&gt;&lt;/span&gt; evidence: System.Web.UI.WebControls.WebControl is rendered as &amp;lt;table &amp;gt;&lt;br /&gt;Mono1.1 doesn't address adaptive Rendering - there is no &amp;lt;browserCaps&amp;gt; in its machine.config&lt;/p&gt; &lt;p&gt;2. Test rendering by IIS6&lt;br /&gt;On MSIE 6.0:  &lt;span style="font-family:courier new,monospace;"&gt;tagwriter=System.Web.UI.&lt;strong&gt;HtmlTextWriter&lt;/strong&gt;&lt;/span&gt;&lt;br /&gt;evidence: System.Web.UI.WebControls.WebControl is rendered as &amp;lt;div&amp;gt;&lt;br /&gt;On FireFox 1.5: &lt;span style="font-family:courier new,monospace;"&gt;tagwriter=System.Web.UI.&lt;strong&gt;Html32TextWriter&lt;/strong&gt;&lt;/span&gt;&lt;br /&gt;evidence: System.Web.UI.WebControls.WebControl is rendered as &amp;lt;table &amp;gt;&amp;lt;tr&amp;gt;&amp;lt;td&amp;gt;&lt;/p&gt;  &lt;p&gt;It seemed that Mono team get around the problem luckily because it was born at a time HTML 4.0-compliant browsers prevails. (At least it was what they thought?). But maybe we can still add &amp;lt;browserCaps&amp;gt; for backward adaptive? At least it looks straightforward enough to add Add &amp;lt;browserCaps&amp;gt; to  web.config to enable mono becomes aptive.&lt;br /&gt;Not quite though.&lt;br /&gt;Checking native .net1.x machine.config, in &amp;lt;configuration&amp;gt;&amp;lt;configSections&amp;gt; there is:&lt;br /&gt;&lt;span style="font-family:courier new,monospace;"&gt;&lt;span style="background-color: rgb(204, 204, 204);"&gt; &amp;lt;section name="browserCaps" type="System.Web.Configuration.HttpCapabilitiesSectionHandler, System.Web, Version=1.0.5000.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a"/&amp;gt;&lt;/span&gt;&lt;br /&gt;&lt;/span&gt;HttpCapabilitiesSectionHandler handles &amp;lt;browserCaps&amp;gt;. However,  mono1.x build System.Web does NOT contain type HttpCapabilitiesSectionHandler implementation.&lt;/p&gt; &lt;p&gt;Conclusion: Mono1.X is not an adaptive ASPNET rendering engine.&lt;/p&gt; &lt;p&gt;Ideally we could add this to Web.config (affect single web app) or machine.config (affect all web apps on the machine)&lt;/p&gt; &lt;p&gt;&amp;lt;configuration&amp;gt;&lt;br /&gt;...&lt;br /&gt;&amp;lt;configSections&amp;gt;&lt;br /&gt;...&lt;br /&gt;&amp;lt;sectionGroup name="system.web"&amp;gt;&lt;br /&gt; &amp;lt;section name="browserCaps" type="System.Web.Configuration.HttpCapabilitiesSectionHandler , System.Web, Version=1.0.5000.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a"/&amp;gt;&lt;br /&gt;...&lt;br /&gt;&amp;lt;/sectionGroup&amp;gt;&lt;br /&gt;&amp;lt;/configSections&amp;gt;&lt;br /&gt;&amp;lt;System.Web&amp;gt;&lt;br /&gt;...&lt;br /&gt;&amp;lt;browserCaps&amp;gt;&lt;br /&gt;&amp;lt;!-- if (working on  web.config) { copy all &amp;lt;browserCaps&amp;gt; section from machine.config} --&amp;gt;&lt;br /&gt;&amp;lt;!-- copy Rob Eberhardt's &amp;lt;browserCaps&amp;gt; (&lt;a href="http://slingfive.com/pages/code/browserCaps/browserCaps_spaces.txt"&gt;http://slingfive.com/pages/code/browserCaps/browserCaps_spaces.txt &lt;/a&gt;) --&amp;gt;&lt;br /&gt;&amp;lt;/browserCaps&amp;gt;&lt;br /&gt;...&lt;br /&gt;&amp;lt;/System.Web&amp;gt;&lt;/p&gt;&lt;p&gt;Technorati Tags: &lt;a href="http://technorati.com/tag/MONO+ASPNET" rel="MONO ASPNET"&gt;MONO ASPNET&lt;/a&gt;&lt;/p&gt;&lt;/div&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-115697877599595408?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/115697877599595408/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=115697877599595408' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/115697877599595408'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/115697877599595408'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2006/08/mono-is-not-adaptive-aspnet-web.html' title='Mono is not an adaptive asp.net web rendering engine'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-115666810198122854</id><published>2006-08-27T09:41:00.000+01:00</published><updated>2006-08-31T00:09:34.436+01:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='nant'/><category scheme='http://www.blogger.com/atom/ns#' term='vs.net'/><title type='text'>Intellisense Nant Build Script on VSNET</title><content type='html'>&lt;p&gt;&lt;span style="font-family:verdana;"&gt;From &lt;a onclick="return top.js.OpenExtLink(window,event,this)" href="http://weblogs.asp.net/soever/archive/2005/02/01/364883.aspx" target="_blank"&gt;Serge van den Oever&lt;/a&gt;&lt;/span&gt; &lt;span style="font-family:verdana;"&gt;&lt;br /&gt;1. Edit and save following build script to NAntGenerateSchema.build. This&lt;br /&gt;script is used to generate the nant.xsd for the Intellisense trick&lt;/span&gt;. &lt;span style="background-color: rgb(204, 204, 204);font-family:courier new,monospace;" &gt;&lt;br /&gt;&amp;lt;?xml version="1.0" encoding="utf-8" ?&amp;gt; &amp;lt;project&lt;br /&gt;name="GenerateNAntSchemaForVS.NET" default="genschema"&amp;gt; &amp;lt;property&lt;br /&gt;name="myVsNetRoot" value="C:\Program Files\Microsoft Visual Studio .NET 2003"&lt;br /&gt;/&amp;gt; &amp;lt;property name="nantSchema"&lt;br /&gt;value="${myVsnetRoot}\Common7\Packages\schemas\xml\NAnt.xsd"/&amp;gt; &amp;lt;target&lt;br /&gt;name="genschema"&amp;gt; &amp;lt;nantschema output="${nantSchema}" target-ns=" &lt;a onclick="return top.js.OpenExtLink(window,event,this)" href="http://nant.sf.net/schemas/nant.xsd" target="_blank"&gt;http://nant.sf.net/schemas/nant.xsd&lt;/a&gt;"/&amp;gt;&lt;br /&gt;&amp;lt;/target&amp;gt; &amp;lt;/project&amp;gt;&lt;/span&gt;&lt;/p&gt;1) update property &lt;span style="font-family:courier new,monospace;"&gt;myVsNetRoot&lt;/span&gt; to &lt;span style="font-family:verdana;"&gt;your VSNET install path.&lt;/span&gt;&lt;br /&gt;&lt;p&gt;&lt;span style="font-family:verdana;"&gt;2) save this script as NAntGenerateSchema.build &lt;/span&gt;&lt;br /&gt;&lt;/p&gt;3) run "nant NAntGenerateSchema.build ' . This will download the latest nant schema from Source Forge to VSNET schema dir. Note: this script should be run when &lt;span style="font-family:verdana;"&gt;refreshing nant releases.&lt;/span&gt;&lt;br /&gt;&lt;p&gt;&lt;span style="font-family:verdana;"&gt;2. Suppose you are working on HelloWorld.sln with VSNET, create a HelloWorld.build, which is your nant build script. Open HelloWorld.build in the IDE ((RC) by open with - HTML/XML Editor (set to default unless you need encoding).&lt;/span&gt;&lt;br /&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="font-family:verdana;"&gt;3. Open the properties window for HelloWorld.build, Select "&lt;a onclick="return top.js.OpenExtLink(window,event,this)" href="http://nant.sf.net/schemas/nant.xsd" target="_blank"&gt; http://nant.sf.net/schemas/nant.xsd&lt;/a&gt;" as TargetSchema.&lt;br /&gt;&lt;br /&gt;Job done.&lt;/span&gt;&lt;br /&gt;&lt;/p&gt;&lt;span style="font-size:85%;"&gt;Technorati Tags:  &lt;a href="http://technorati.com/tag/NANT+VSNET" rel="NANT VSNET"&gt;NANT VSNET&lt;/a&gt;&lt;/span&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-115666810198122854?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/115666810198122854/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=115666810198122854' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/115666810198122854'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/115666810198122854'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2006/08/intellisense-nant-build-script-on.html' title='Intellisense Nant Build Script on VSNET'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-115655341228142063</id><published>2006-08-26T01:50:00.000+01:00</published><updated>2006-08-28T23:58:39.033+01:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='ruby'/><category scheme='http://www.blogger.com/atom/ns#' term='nant'/><category scheme='http://www.blogger.com/atom/ns#' term='asp.net'/><category scheme='http://www.blogger.com/atom/ns#' term='tdd'/><category scheme='http://www.blogger.com/atom/ns#' term='mono'/><category scheme='http://www.blogger.com/atom/ns#' term='nunit'/><title type='text'>nAnt build script to test mono web app with Ruby and Watir</title><content type='html'>&lt;p style="font-weight: bold;"&gt;Download the build script template: &lt;a href="http://comingup.nemonova.com/myWebsite.build"&gt;myWebsite.build&lt;/a&gt;&lt;/p&gt;&lt;strong&gt;1. Prove nant task &amp;lt;csc&amp;gt;, &amp;lt;nunit2&amp;gt; works/doesn't work with mono&lt;br /&gt; build&lt;/strong&gt;&lt;br /&gt;&lt;ol&gt;&lt;li&gt;  Prove test assembly is fine use vsnet (.net 1.1) build, reference *.net1.1*&lt;br /&gt; nunit.framework.dll , not the mono build.&lt;br /&gt; &lt;ul&gt;&lt;br /&gt;  &lt;li&gt;build asm&lt;br /&gt;  &lt;/li&gt;&lt;li&gt;tested with nUnit2.2.0 GUI exe&lt;br /&gt;  &lt;/li&gt;&lt;li&gt;tested with nUnit-2.2.0-mono console exe.&lt;/li&gt;&lt;/ul&gt;&lt;br /&gt; Both work as expected&lt;br /&gt;&lt;/li&gt;&lt;br /&gt;&lt;li&gt;nAnt build. nant target mono-1.0; reference lib (nunit.framework.dll) set to NUnit-2.2.0-mono&lt;br /&gt; &lt;ul&gt;&lt;br /&gt;  &lt;li&gt;test assembly with nUnit2.2.0 GUI exe. On loading asm it throws exception&lt;br /&gt;   'This assembly was not built with the NUNIT framework and contains no tests'&lt;br /&gt;   cases' on the popout message window&lt;/li&gt;&lt;li&gt;test assembly with nUnit-2.2.0-mono&lt;br /&gt;   console exe. This returns:&lt;br /&gt;   &lt;div style="font-family: courier new; background-color: rgb(204, 204, 204);"&gt;OS Version: Microsoft Windows NT 5.1.2600.0 .NET Version: 1.1.4322.2032 Tests run:&lt;br /&gt;    0, Failures: 0, Not run: 0, Time: 0 seconds Open the assembly by .net&lt;br /&gt;    reflector, surprise, surpise there is nothing in the dll&lt;br /&gt;&lt;/div&gt;&lt;/li&gt;&lt;/ul&gt;&lt;/li&gt;&lt;/ol&gt;&lt;strong&gt;2. Use mono mcs compiler&lt;/strong&gt;&lt;br /&gt;&lt;ol&gt;&lt;li&gt;  compiles the source&lt;br /&gt; &lt;div style="font-family: courier new; background-color: rgb(204, 204, 204);"&gt;mcs -r:system.dll -r:\sslocal\Cenote.root\dependencies\NUnit-&lt;br /&gt;  2.2.0-mono\bin\nunit.framework.dll -t:library SampleRubyTestFixture.cs&lt;/div&gt;&lt;br /&gt;&lt;/li&gt;&lt;li&gt;  test - test assembly with nUnit2.2.0 GUI exe. - test assembly with&lt;br /&gt; nUnit-2.2.0-mono console exe. - test assembly with nUnit2.2.8 GUI exe. All work&lt;br /&gt; as expected&lt;br /&gt;&lt;/li&gt;&lt;br /&gt;&lt;li&gt;Open the assembly by .net reflector, it confirms that our test case is in there This confirms that nUnit2.2.* GUI exe doesn't discriminate mono build, as long as nunit.framework.dll is the .net1.1 compliance version This also confirms that the problem is not with nant task &amp;lt;nUnit2&amp;gt;, regardless which nunit build version it points to.&lt;br /&gt;&lt;/li&gt;&lt;/ol&gt;&lt;strong&gt;3. Questioning nant task &amp;lt;csc&amp;gt;&lt;/strong&gt;&lt;br /&gt;Before setting off to use task &amp;lt;exec&amp;gt; and mcs for the build, I have a few more go on task &amp;lt;csc&amp;gt;. Eventually it confirms that it was a bug in the &amp;lt;csc&amp;gt; task causes the problem.&lt;br /&gt;nAnt doesn't support multiple filesets or its derived types like assemblyfileset etc, which means you cann't resuse reference assemblyfileset. For building multiple projects in a build that each project has an inter-set to others, each &amp;lt;csc&amp;gt; needs to have a full list of &amp;lt;reference&amp;gt;&amp;lt;include&amp;gt; dlls. A bit of pain. Using &amp;lt;module&amp;gt; is a hack. Though it solves the resuse problem on the surface, if you poke the assembly with Reflector, you will find there are modules should really be references. this is NOT the right way to reference &amp;lt;assemblyfileset&amp;gt;.&lt;br /&gt;&lt;div style="font-family: courier new,monospace; background-color: rgb(204, 204, 204);"&gt;&amp;lt;csc&amp;gt; ... &amp;lt;references refid="sys.assemblies " /&amp;gt; &amp;lt;modules&amp;gt;&lt;br /&gt;&amp;lt;include name="${webcontrols.output.Mono}\${webcontrolsNamespace}.dll" /&amp;gt;&lt;br /&gt;&amp;lt;include name="${cenote.output.Mono}\${cenoteNamespace}.dll" /&amp;gt;&lt;br /&gt;&amp;lt;/modules&amp;gt; &amp;lt;/csc&amp;gt;&lt;/div&gt;&lt;br /&gt;By the way, if declare &amp;lt;fileset&amp;gt;and its derived types like&lt;br /&gt;&amp;lt;assemblyfileset&amp;gt; at project level(doc root) it can take an id attribue&lt;br /&gt;and can be referenced from everywhere.&lt;br /&gt;&lt;strong&gt;4. &amp;lt;nunit2&amp;gt; and nUnit2.2.x GUI&lt;/strong&gt;&lt;br /&gt;Leaving the bug in &amp;lt;csc&amp;gt; behind, I move into nant &amp;lt;target&amp;gt; unit&lt;br /&gt;test with &amp;lt;nunit2&amp;gt;. nunit2 used nunit-version="&lt;a href="http://2.2.8.0/"&gt; 2.2.8.0&lt;/a&gt;"&lt;br /&gt;clr-version="2.0.50727.42" for the test. Passed. However, now the mono-target&lt;br /&gt;assemble is not loaded with nUnit2.2.X GUI, not even nUnit-2.2.0-mono console&lt;br /&gt;exe. An System.IO.FileNotFoundException is thrown, complaining test dll or its&lt;br /&gt;dependencies dlls are not found. [to-do] I will look into it later. This is not&lt;br /&gt;an issue for next step. (We only use nUnit gui for vsnet build)&lt;br /&gt;&lt;strong&gt;5. Serve web test using ruby+watir&lt;/strong&gt;&lt;br /&gt;prerequisite: install &lt;a href="http://rubyforge.org/projects/rubyinstaller/"&gt;Ruby&lt;/a&gt;&lt;br /&gt;engine and &lt;a href="http://rubyforge.org/frs/?group_id=104"&gt;Watir&lt;/a&gt; library&lt;br /&gt;Watir offers a clean, well define, automated and scripting (in opposite to&lt;br /&gt;recording) base Web app test. &lt;a href="http://www.codeproject.com/cpnet/RubyTestExecutor.asp"&gt;&lt;br /&gt;Travis&lt;/a&gt; made a nice hook to integrate ruby script into nUnit test&lt;br /&gt;framework. It is not absolutely necessary to integrate ruby script into nUnit.&lt;br /&gt;*.rb script can run from cmd line. However, the integration leverage the&lt;br /&gt;reporting function comes with nUnit.&lt;br /&gt;&lt;ol&gt;&lt;li&gt;compile RubyTestExecutor-1.1.3.0 to target nunit_2.2.0_mono&lt;br /&gt;&lt;/li&gt;&lt;li&gt;Write a 'Hello World' test case as well as ruby script. In Nant task&lt;br /&gt; &amp;lt;csc&amp;gt;include them as embeded resource. &amp;lt;resources&lt;br /&gt; dynamicprefix="true"&amp;gt; &amp;lt;include name="...\*.rb" /&amp;gt; &amp;lt;/resources&amp;gt;&lt;br /&gt;&lt;/li&gt;&lt;li&gt;VSNET .net1.1 build and nUnit GUI test&lt;br /&gt; &lt;ul&gt;&lt;br /&gt;  &lt;li&gt;in vsnet reference RubyTestExecutor-1.1.3.0_target_nunit_2.2.0&lt;br /&gt;  &lt;/li&gt;&lt;li&gt;make sure the Web_Control_test_project is set to default web sharing. It&lt;br /&gt;   contains test pages as well as test cases.&lt;br /&gt;  &lt;/li&gt;&lt;li&gt;Postbuild action to copy test.dll and referenced dlls (except&lt;br /&gt;   nUnit.framework.dll) from ~\bin\Debug to ~\bin&lt;br /&gt;  &lt;/li&gt;&lt;li&gt;run tests&lt;/li&gt;&lt;/ul&gt;&lt;/li&gt;&lt;br /&gt;&lt;li&gt;VSNET mono1.0 build and nAnt build (test with &amp;lt;nunit2&amp;gt;, on my pc it picks&lt;br /&gt; the lastest nunit2.2.8 engine)&lt;br /&gt; &lt;ul&gt;&lt;br /&gt;  &lt;li&gt;in nAnt build reference RubyTestExecutor-1.1.3.0_target_nunit_2.2.0_mono&lt;br /&gt;  &lt;/li&gt;&lt;li&gt;compile, delpoy as usual&lt;br /&gt;  &lt;/li&gt;&lt;li&gt;start XSP at Web_Control_test_project where pages live.&lt;br /&gt;  &lt;/li&gt;&lt;li&gt;Both use port 80 for http request. This means we don't need to change ruby&lt;br /&gt;   scripts for native 1.1 (which runs on IIS) or mono runtime (which runs XSP).&lt;br /&gt;   Just need to stop/start IIS before XSP kicks start. (I argue it is more&lt;br /&gt;   pragmatic then dynamic decide which port to use depends on runtime env)&lt;/li&gt;&lt;/ul&gt;&lt;/li&gt;&lt;/ol&gt;&lt;strong&gt;5 Conclusion&lt;/strong&gt;&lt;br /&gt;With this build script, we archieve:&lt;br /&gt;&lt;ul&gt;&lt;li&gt;  Implement, build and test ASP.Net Web Controls and Website in VSNET2003 IDE to&lt;br /&gt; target .Net 1.1 framework.&lt;br /&gt;&lt;/li&gt;&lt;li&gt;  Use nAnt build script to link, compile, deploy the same code base to target&lt;br /&gt; Mono1.0. This build process needs to know nothing about the IDE build.&lt;br /&gt;&lt;/li&gt;&lt;li&gt;  Use Ruby+Watir scripts to test web app in 'nearest' real way.The script test&lt;br /&gt; suite is seamlessly integrate into nUnit framework.&lt;/li&gt;&lt;/ul&gt;&lt;strong&gt;6 What's more can be done?&lt;/strong&gt;&lt;br /&gt;Automated XSP web server start/stop. The build process requires manually start&lt;br /&gt;mono XSP web server before &amp;lt;nunit2&amp;gt; tests. XSP must run in an isolated&lt;br /&gt;AppDomain/process from where nAnt is running from, so use &amp;lt;exec&amp;gt; task is&lt;br /&gt;not prossible. It is also not possible to use &lt;a href="http://www.gotdotnet.com/team/clr/AppdomainFAQ.aspx"&gt;&lt;br /&gt;&lt;span class="pageTitle"&gt;&lt;span id="ctl01_PageTitleLabel"&gt;Application Domain&lt;br /&gt;  ExecuteAssembly&lt;/span&gt;&lt;/span&gt;&lt;/a&gt; to create and load XSP into an&lt;br /&gt;isolated AppDomain because on Windows OS XSP requires mono runtime environment,&lt;br /&gt;which is unmanaged code. (Though XSP.exe is managed code.)&lt;br /&gt;&lt;p&gt;Download the build script template: &lt;a style="font-weight: bold;" href="http://comingup.nemonova.com/myWebsite.build"&gt;myWebsite.build&lt;/a&gt;&lt;br /&gt;&lt;/p&gt;Technorati Tags: &lt;a href="http://technorati.com/tag/Nant" rel="nAnt"&gt;nAnt&lt;/a&gt;&lt;br /&gt;&lt;div&gt;&lt;a href="http://technorati.com/tag/RUBY+WATIR" rel="RUBY"&gt;  RUBY WATIR&lt;/a&gt; &lt;a href="http://technorati.com/tag/MONO+ASPNET" rel="MONO ASPNET"&gt;&lt;br /&gt; MONO ASPNET&lt;/a&gt;&lt;br /&gt;&lt;/div&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-115655341228142063?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/115655341228142063'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/115655341228142063'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2006/08/nant-build-script-to-test-mono-web-app.html' title='nAnt build script to test mono web app with Ruby and Watir'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-115607279081463280</id><published>2006-08-20T12:19:00.000+01:00</published><updated>2006-08-20T12:27:58.940+01:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='ruby'/><category scheme='http://www.blogger.com/atom/ns#' term='tdd'/><category scheme='http://www.blogger.com/atom/ns#' term='nunit'/><title type='text'>TDD Mono asp.net web application on</title><content type='html'>&lt;div class="MsoNormal"  style="margin: 0cm 0cm 0pt;font-family:verdana;"&gt;&lt;span style="font-size:85%;"&gt;Note: (This is a dump as I play with the new tools on doing familiar TDD aka. Test Driven Development), &lt;em&gt;work in progress&lt;/em&gt;.&lt;/span&gt;&lt;/div&gt;  &lt;div class="MsoNormal"  style="margin: 0cm 0cm 0pt;font-family:verdana;"&gt;&lt;span style="font-size:85%;"&gt;&lt;strong&gt;&lt;/strong&gt; &lt;/span&gt;&lt;/div&gt; &lt;div class="MsoNormal"  style="margin: 0cm 0cm 0pt;font-family:verdana;"&gt;&lt;span style="font-size:85%;"&gt;&lt;strong&gt;&lt;br /&gt;The application:  &lt;/strong&gt;An &lt;a href="http://asp.net/"&gt;asp.net&lt;/a&gt; web application run on Linux Mono&lt;br /&gt;&lt;br /&gt;&lt;/span&gt;&lt;/div&gt; &lt;div class="MsoNormal"  style="margin: 0cm 0cm 0pt;font-family:verdana;"&gt;&lt;span style="font-size:85%;"&gt; &lt;/span&gt;&lt;/div&gt; &lt;div class="MsoNormal"  style="margin: 0cm 0cm 0pt;font-family:verdana;"&gt;&lt;span style="font-size:85%;"&gt;&lt;strong&gt;Requirement: Unit test web application UI.&lt;/strong&gt;&lt;/span&gt;&lt;/div&gt; &lt;p class="MsoNormal"  style="margin: 0cm 0cm 0pt 36pt; text-indent: -18pt;font-family:verdana;"&gt;&lt;span style="font-size:85%;"&gt;–&lt;span style="font-style: normal; font-variant: normal; font-weight: normal; line-height: normal; font-size-adjust: none; font-stretch: normal;"&gt;         &lt;/span&gt;&lt;/span&gt;&lt;span style="font-size:85%;"&gt;&lt;i style=""&gt;This is hard. &lt;/i&gt;NUNIT is designed for API (exe, lib) test&lt;/span&gt;&lt;/p&gt; &lt;p class="MsoNormal"  style="margin: 0cm 0cm 0pt 36pt; text-indent: -18pt;font-family:verdana;"&gt;&lt;span style="font-size:85%;"&gt;–&lt;span style="font-style: normal; font-variant: normal; font-weight: normal; line-height: normal; font-size-adjust: none; font-stretch: normal;"&gt;         &lt;/span&gt;&lt;/span&gt;&lt;span style="font-size:85%;"&gt;Unit test server controls&lt;/span&gt;&lt;/p&gt; &lt;p class="MsoNormal"  style="margin: 0cm 0cm 0pt 36pt; text-indent: -18pt;font-family:verdana;"&gt;&lt;span style="font-size:85%;"&gt;–&lt;span style="font-style: normal; font-variant: normal; font-weight: normal; line-height: normal; font-size-adjust: none; font-stretch: normal;"&gt;         &lt;/span&gt;&lt;/span&gt;&lt;span style="font-size:85%;"&gt;Support Continuous integration &lt;/span&gt;&lt;/p&gt; &lt;p class="MsoNormal"  style="margin: 0cm 0cm 0pt;font-family:verdana;"&gt;&lt;span style="font-size:85%;"&gt; &lt;/span&gt;&lt;/p&gt; &lt;p class="MsoNormal"  style="margin: 0cm 0cm 0pt;font-family:verdana;"&gt;&lt;span style="font-size:85%;"&gt;&lt;strong&gt;&lt;br /&gt;&lt;/strong&gt;&lt;/span&gt;&lt;/p&gt;&lt;p class="MsoNormal"  style="margin: 0cm 0cm 0pt;font-family:verdana;"&gt;&lt;span style="font-size:85%;"&gt;&lt;strong&gt;Tools for the trade:&lt;/strong&gt;&lt;/span&gt;&lt;/p&gt; &lt;p class="MsoNormal"  style="margin: 0cm 0cm 0pt 36pt; text-indent: -18pt;font-family:verdana;"&gt;&lt;span style="font-size:85%;"&gt;-&lt;span style="font-style: normal; font-variant: normal; font-weight: normal; line-height: normal; font-size-adjust: none; font-stretch: normal;"&gt;          &lt;/span&gt;&lt;/span&gt;&lt;span style="font-size:85%;"&gt;VS.net IDE&lt;/span&gt;&lt;/p&gt; &lt;p class="MsoNormal"  style="margin: 0cm 0cm 0pt 36pt; text-indent: -18pt;font-family:verdana;"&gt;&lt;span style="font-size:85%;"&gt;-&lt;span style="font-style: normal; font-variant: normal; font-weight: normal; line-height: normal; font-size-adjust: none; font-stretch: normal;"&gt;          &lt;/span&gt;&lt;/span&gt;&lt;span style="font-size:85%;"&gt;&lt;a href="http://www.nunit.org/index.php?p=download"&gt;NUnit&lt;/a&gt; (For this project we targeting &lt;a href="http://asp.net/"&gt;asp.net&lt;/a&gt;  1.1, so pick NUnit 2.2 from the list)&lt;/span&gt;&lt;/p&gt; &lt;p class="MsoNormal"  style="margin: 0cm 0cm 0pt 36pt; text-indent: -18pt;font-family:verdana;"&gt;&lt;span style="font-size:85%;"&gt;-&lt;span style="font-style: normal; font-variant: normal; font-weight: normal; line-height: normal; font-size-adjust: none; font-stretch: normal;"&gt;          &lt;/span&gt;&lt;/span&gt;&lt;span style="font-size:85%;"&gt;Nant&lt;/span&gt;&lt;/p&gt; &lt;p class="MsoNormal"  style="margin: 0cm 0cm 0pt 36pt; text-indent: -18pt;font-family:verdana;"&gt;&lt;span style="font-size:85%;"&gt;-&lt;span style="font-style: normal; font-variant: normal; font-weight: normal; line-height: normal; font-size-adjust: none; font-stretch: normal;"&gt;          &lt;/span&gt;&lt;/span&gt;&lt;span style="font-size:85%;"&gt;&lt;a href="http://rubyforge.org/projects/rubyinstaller/"&gt;Ruby&lt;/a&gt;&lt;/span&gt;&lt;/p&gt; &lt;p class="MsoNormal"  style="margin: 0cm 0cm 0pt 36pt; text-indent: -18pt;font-family:verdana;"&gt;&lt;span style="font-size:85%;"&gt;-&lt;span style="font-style: normal; font-variant: normal; font-weight: normal; line-height: normal; font-size-adjust: none; font-stretch: normal;"&gt;          &lt;/span&gt;&lt;/span&gt;&lt;span style="font-size:85%;"&gt;&lt;a href="http://rubyforge.org/frs/?group_id=104"&gt;WATIR&lt;/a&gt; (I use &lt;a href="http://rubyforge.org/frs/download.php/5677/watir-1.4.1.exe"&gt; watir-1.4.1.exe&lt;/a&gt; as at the time of writing)&lt;/span&gt;&lt;/p&gt; &lt;p class="MsoNormal"  style="margin: 0cm 0cm 0pt 36pt; text-indent: -18pt;font-family:verdana;"&gt;&lt;span style="font-size:85%;"&gt;-&lt;span style="font-style: normal; font-variant: normal; font-weight: normal; line-height: normal; font-size-adjust: none; font-stretch: normal;"&gt;          &lt;/span&gt;&lt;/span&gt;&lt;span style="font-size:85%;"&gt;Mono gtk,&lt;/span&gt;&lt;span style="font-size:85%;"&gt;   &lt;/span&gt;&lt;span style="font-size:85%;"&gt;XSP web server&lt;/span&gt;&lt;/p&gt; &lt;p class="MsoNormal"  style="margin: 0cm 0cm 0pt 18pt;font-family:verdana;"&gt;&lt;span style="font-size:85%;"&gt; &lt;/span&gt;&lt;/p&gt; &lt;p class="MsoNormal"  style="margin: 0cm 0cm 0pt;font-family:verdana;"&gt;&lt;span style="font-size:85%;"&gt;&lt;strong&gt;&lt;br /&gt;&lt;/strong&gt;&lt;/span&gt;&lt;/p&gt;&lt;p class="MsoNormal"  style="margin: 0cm 0cm 0pt;font-family:verdana;"&gt;&lt;span style="font-size:85%;"&gt;&lt;strong&gt;Internal Resource:&lt;/strong&gt;&lt;/span&gt;&lt;/p&gt; &lt;p class="MsoNormal"  style="margin: 0cm 0cm 0pt 36pt; text-indent: -18pt;font-family:verdana;"&gt;&lt;span style="font-size:85%;"&gt;-&lt;span style="font-style: normal; font-variant: normal; font-weight: normal; line-height: normal; font-size-adjust: none; font-stretch: normal;"&gt;          &lt;/span&gt;&lt;/span&gt;&lt;span style="font-size:85%;"&gt;Ruby test code template for &lt;a href="http://vs.net/"&gt;vs.net&lt;/a&gt;&lt;/span&gt;&lt;/p&gt; &lt;p class="MsoNormal"  style="margin: 0cm 0cm 0pt 36pt; text-indent: -18pt;font-family:verdana;"&gt;&lt;span style="font-size:85%;"&gt;-&lt;span style="font-style: normal; font-variant: normal; font-weight: normal; line-height: normal; font-size-adjust: none; font-stretch: normal;"&gt;          &lt;/span&gt;&lt;/span&gt;&lt;span style="font-size:85%;"&gt;Water code template for &lt;a href="http://vs.net/"&gt;vs.net&lt;/a&gt;&lt;/span&gt;&lt;span style="font-size:85%;"&gt;  &lt;/span&gt;&lt;span style="font-size:85%;"&gt;(because I am lazy)&lt;/span&gt;&lt;/p&gt; &lt;p class="MsoNormal"  style="margin: 0cm 0cm 0pt;font-family:verdana;"&gt;&lt;span style="font-size:85%;"&gt; &lt;/span&gt;&lt;/p&gt; &lt;p class="MsoNormal"  style="margin: 0cm 0cm 0pt;font-family:verdana;"&gt;&lt;span style="font-size:85%;"&gt;&lt;strong&gt;&lt;br /&gt;&lt;/strong&gt;&lt;/span&gt;&lt;/p&gt;&lt;p class="MsoNormal"  style="margin: 0cm 0cm 0pt;font-family:verdana;"&gt;&lt;span style="font-size:85%;"&gt;&lt;strong&gt;Reference:&lt;/strong&gt;&lt;/span&gt;&lt;/p&gt; &lt;p class="MsoNormal"  style="margin: 0cm 0cm 0pt;font-family:verdana;"&gt;&lt;span style="font-size:85%;"&gt;&lt;a href="http://secretgeek.net/watir_3mins.asp"&gt;&lt;span style="color: rgb(128, 0, 128);"&gt;Babysteps in WATIR&lt;/span&gt;&lt;/a&gt; A Jumpstart to Ruby/Watir &lt;/span&gt;&lt;/p&gt; &lt;p class="MsoNormal"  style="margin: 0cm 0cm 0pt;font-family:verdana;"&gt;&lt;span style="font-size:85%;"&gt; &lt;/span&gt;&lt;/p&gt; &lt;p class="MsoNormal"  style="margin: 0cm 0cm 0pt;font-family:verdana;"&gt;&lt;span style="font-size:85%;"&gt;&lt;a href="http://www.codeproject.com/cpnet/RubyTestExecutor.asp"&gt;Integrated ASP.NET Web Application Testing with NUnit, Ruby, and Watir &lt;/a&gt; &lt;/span&gt;&lt;span style="font-size:85%;"&gt;Travis Illig creates a RubyTestExecutor to integrate Ruby/Watir Testscripts into nUnit framework. So test cases can be run from GUI like other nUnit test cases. However this is more of convenience that necessary. You still write Ruby/Watir scripts. You can still invoke them from command line. &lt;/span&gt;&lt;/p&gt; &lt;p class="MsoNormal"  style="margin: 0cm 0cm 0pt;font-family:verdana;"&gt;&lt;span style="font-size:85%;"&gt; &lt;/span&gt;&lt;/p&gt; &lt;p class="MsoNormal"  style="margin: 0cm 0cm 0pt;font-family:verdana;"&gt;&lt;span style="font-size:85%;"&gt;&lt;a href="http://www.codeproject.com/cpnet/introtomono1.asp"&gt;Introduction to Mono - Your first Mono app&lt;/a&gt; &lt;/span&gt;&lt;span style="font-size:85%;"&gt;  &lt;/span&gt;&lt;span style="font-size:85%;"&gt;Happened to find this Primer&lt;/span&gt;&lt;/p&gt; &lt;p class="MsoNormal"  style="margin: 0cm 0cm 0pt;font-family:verdana;"&gt;&lt;span style="font-size:85%;"&gt; &lt;/span&gt;&lt;/p&gt; &lt;p class="MsoNormal"  style="margin: 0cm 0cm 0pt;font-family:verdana;"&gt;&lt;span style="font-size:85%;"&gt;&lt;strong&gt;&lt;br /&gt;&lt;/strong&gt;&lt;/span&gt;&lt;/p&gt;&lt;p class="MsoNormal"  style="margin: 0cm 0cm 0pt;font-family:verdana;"&gt;&lt;span style="font-size:85%;"&gt;&lt;strong&gt;Development pattern:&lt;/strong&gt;&lt;/span&gt;&lt;/p&gt; &lt;p class="MsoNormal"  style="margin: 0cm 0cm 0pt;font-family:verdana;"&gt;&lt;span style="font-size:85%;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;/p&gt;&lt;p class="MsoNormal"  style="margin: 0cm 0cm 0pt;font-family:verdana;"&gt;&lt;span style="font-size:85%;"&gt;Assumption: Coding in &lt;a href="http://vs.net/"&gt;vs.net&lt;/a&gt; 2003, OS: winXP&lt;/span&gt;&lt;/p&gt; &lt;p class="MsoNormal"  style="margin: 0cm 0cm 0pt;font-family:verdana;"&gt;&lt;span style="font-size:85%;"&gt; &lt;/span&gt;&lt;/p&gt; &lt;p class="MsoNormal"  style="margin: 0cm 0cm 0pt;font-family:verdana;"&gt;&lt;span style="font-size:85%;"&gt;(One off task) Create web project&lt;/span&gt;&lt;/p&gt; &lt;ol  style="margin-top: 0cm;font-family:verdana;" type="1"&gt; &lt;li class="MsoNormal" style="margin: 0cm 0cm 0pt;"&gt;&lt;span style="font-size:85%;"&gt;create project directory: {root}\My.Hello.World&lt;/span&gt;&lt;/li&gt; &lt;li class="MsoNormal" style="margin: 0cm 0cm 0pt;"&gt;&lt;span style="font-size:85%;"&gt;Web share this folder&lt;/span&gt;&lt;/li&gt; &lt;li class="MsoNormal" style="margin: 0cm 0cm 0pt;"&gt;&lt;span style="font-size:85%;"&gt;create a new web project in &lt;a href="http://vs.net/"&gt;vs.net&lt;/a&gt;, map it to My.Hello.World&lt;/span&gt; &lt;/li&gt; &lt;li class="MsoNormal" style="margin: 0cm 0cm 0pt;"&gt;&lt;span style="font-size:85%;"&gt;Execute Mono run time test. Bring up command line console and do nAnt build.&lt;br /&gt;a. Start Mono XSP web server&lt;br /&gt;b. nAnt target doesn't natively require nUnit, although it could leverage point 1-3.&lt;br /&gt;c. However, this is redundant. We can just load up Ruby and Watir script engines and call test scripts&lt;/span&gt;&lt;/li&gt;&lt;/ol&gt;&lt;span style=";font-family:Times New Roman;font-size:85%;"  &gt;  &lt;/span&gt;&lt;span style=";font-family:Times New Roman;font-size:85%;"  &gt; &lt;/span&gt; &lt;div class="MsoNormal"  style="margin: 0cm 0cm 0pt;font-family:verdana;"&gt;&lt;span style="font-size:85%;"&gt;Technorati Tags: &lt;a href="http://technorati.com/tag/TDD" rel="TDD"&gt;TDD&lt;/a&gt; &lt;a href="http://technorati.com/tag/RUBY+WATIR" rel="RUBY"&gt;RUBY WATIR&lt;/a&gt; &lt;a href="http://technorati.com/tag/NUNIT+ASPNET" rel="NUNIT ASPNET"&gt;NUNIT ASPNET &lt;/a&gt;&lt;/span&gt;&lt;/div&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-115607279081463280?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/115607279081463280/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=115607279081463280' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/115607279081463280'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/115607279081463280'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2006/08/tdd-mono-aspnet-web-application-on.html' title='TDD Mono asp.net web application on'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-115565623204538057</id><published>2006-08-15T16:37:00.000+01:00</published><updated>2006-08-15T16:37:14.173+01:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='source control'/><title type='text'>svn external steps</title><content type='html'>&lt;div&gt;This quick note gives a step by stop guide to make svn external reference.&lt;/div&gt; &lt;div&gt; &lt;/div&gt; &lt;div&gt;svn external means that local copy is a references to repository rather than a working copy. So if later checking in would not check-in the local copy, but mark the reference only.&lt;/div&gt; &lt;div&gt; &lt;/div&gt; &lt;div&gt;1. {local path}mkdir dependencies. dependencies contains a collections of external denpendencise (references) we will import next.&lt;/div&gt; &lt;div&gt;2. svn add dependencies {repository url}, and &lt;/div&gt; &lt;div&gt;3. svn ci -m"..." dependencies.  2. 3. source controls 'dependencies'&lt;/div&gt; &lt;div&gt;4. (use windows file browser), go to 'dependencies' |(right click)|Properties|Subverion tab| (requires Tortoise, the svn windows client) &lt;/div&gt; &lt;div&gt;5. from the Subverion tab, select 'svn externals' from middle dropdown box, then in the text area below, type '3rdAPILib url_to_3rdAPILib' (no*'*, 3rdAPILib is the dir name you give to the external reference, url_to_3rdAPILib is its location in the repository) &lt;/div&gt; &lt;div&gt;6. click 'set' button, then 'ok' it.&lt;/div&gt; &lt;div&gt;7. right click 'dependencies'|'SVN Update'. This should get a copy of '3rdAPILib' to your {local path}\dependencies .&lt;/div&gt; &lt;div&gt; &lt;/div&gt; &lt;div&gt;Technorati Tags: &amp;lt;a href="&lt;a href="http://technorati.com/tag/Subversion"&gt;http://technorati.com/tag/Subversion&lt;/a&gt;" rel="tag"&amp;gt;Subversion&amp;lt;/a&amp;gt; &amp;lt;a href=" &lt;a href="http://technorati.com/tag/SVN"&gt; http://technorati.com/tag/SVN&lt;/a&gt;" rel="tag"&amp;gt;SVN&amp;lt;/a&amp;gt;&lt;/div&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-115565623204538057?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/115565623204538057/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=115565623204538057' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/115565623204538057'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/115565623204538057'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2006/08/svn-external-steps.html' title='svn external steps'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-115482169773208149</id><published>2006-08-06T00:48:00.000+01:00</published><updated>2006-08-06T00:56:44.836+01:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='web 2.0'/><title type='text'>Google 1.0 vs Yahoo 2.0</title><content type='html'>&lt;p class="MsoNormal"  style="margin: 0cm 0cm 0pt;font-family:verdana;"&gt;In the book &lt;span style=""&gt;&lt;a href="http://www.amazon.co.uk/gp/product/1857883616/"&gt;The Search&lt;/a&gt;, John Battelle&lt;/span&gt;  compares Yahoo and Google:&lt;/p&gt;&lt;p class="MsoNormal"  style="margin: 0cm 0cm 0pt;font-family:verdana;"&gt;&lt;br /&gt;&lt;/p&gt; &lt;p class="MsoNormal"  style="margin: 0cm 0cm 0pt;font-family:verdana;"&gt; &lt;/p&gt; &lt;p class="MsoNormal" face="verdana" style="margin: 0cm 0cm 0pt;"&gt;&lt;i style=""&gt;"Yahoo makes no pretence of objectivity-it is clearly steering searchers toward its own editorial services, which it believes can satisfy the intent of the search. In effect, Yahoo is saying 'You're looking for stuff on Usher? We got stuff on Usher, and it's good stuff. Try what we suggest; we think it'll be worth your time."&lt;/i&gt;&lt;/p&gt;&lt;p class="MsoNormal" face="verdana" style="margin: 0cm 0cm 0pt;"&gt;&lt;i style=""&gt;&lt;br /&gt;&lt;/i&gt;&lt;/p&gt; &lt;p class="MsoNormal" face="verdana" style="margin: 0cm 0cm 0pt;"&gt;&lt;i style=""&gt;"Apparent in that sentiment lies a key distinction between Google and Yahoo. Yahoo is far more willing to have overt editorial and commercial agendas, and to let humans intervene in search results so as to create media that supports those agendas. Google, on the other hand, is repelled by the idea of becoming a content- or editorially driven company…they approach the task with vastly different stances. &lt;span style=""&gt;  &lt;/span&gt;Google sees the problem as one that can be solved mainly through technology-clever algorithms and sheer computational horsepower will prevail. Humans enter the search picture only when algorithms fail and then only grudgingly."&lt;/i&gt;&lt;/p&gt;&lt;p class="MsoNormal" face="verdana" style="margin: 0cm 0cm 0pt;"&gt;&lt;i style=""&gt;&lt;br /&gt;&lt;/i&gt;&lt;/p&gt; &lt;p class="MsoNormal" face="verdana" style="margin: 0cm 0cm 0pt;"&gt; &lt;/p&gt; &lt;p class="MsoNormal" face="verdana" style="margin: 0cm 0cm 0pt;"&gt;What Battelle makes is that Google's approach – using technology- 'the machine' and algorithm to solve indexing world's information. I tend to think of it as 'content based' search: index based on content text rather than the semantic meaning of it and search based on keyword appearances and PageRank to decide its weight.&lt;/p&gt;&lt;p class="MsoNormal" face="verdana" style="margin: 0cm 0cm 0pt;"&gt;&lt;br /&gt;&lt;span style=""&gt; &lt;/span&gt;&lt;/p&gt; &lt;p class="MsoNormal" style="margin: 0cm 0cm 0pt; font-family: verdana;"&gt; &lt;/p&gt; &lt;p class="MsoNormal" style="margin: 0cm 0cm 0pt; font-family: verdana;"&gt;On the other hand Yahoo is taking an editorial approach on searching. It integrates human to drive search, helping searchers force on search intention. 'What you are really looking for?' By typing search keyword  &lt;span style=""&gt; &lt;/span&gt;'Usher' do you mean music artist Usher's lyrics or buying an Usher' music CD?&lt;/p&gt;&lt;p class="MsoNormal" style="margin: 0cm 0cm 0pt; font-family: verdana;"&gt;&lt;br /&gt;&lt;/p&gt; &lt;p class="MsoNormal" style="margin: 0cm 0cm 0pt; font-family: verdana;"&gt; &lt;/p&gt; &lt;p class="MsoNormal" style="margin: 0cm 0cm 0pt; font-family: verdana;"&gt;In my opinion this intention based search is one step higher than content based search, though it intrinsically comes with scalability issue. How many people Yahoo needs to satisfy the world?&lt;/p&gt;&lt;p class="MsoNormal" style="margin: 0cm 0cm 0pt; font-family: verdana;"&gt;&lt;br /&gt;&lt;span style=""&gt; &lt;/span&gt;&lt;span style=""&gt; &lt;/span&gt;&lt;/p&gt; &lt;p class="MsoNormal" style="margin: 0cm 0cm 0pt; font-family: verdana;"&gt; &lt;/p&gt; &lt;p class="MsoNormal" style="margin: 0cm 0cm 0pt; font-family: verdana;"&gt;Here is where Web 2.0 cutting in. The essence of &lt;a href="http://en.wikipedia.org/wiki/Web_2.0"&gt;Web 2.0 &lt;/a&gt; is collaborate and share information. Build social network by interaction of surfers. Web users self-govern, actively participate in virtual communities, engaging with each other. Web users can also help each other on driving intent based search using new emerging technology like  &lt;a href="http://en.wikipedia.org/wiki/Tags"&gt;tagging&lt;/a&gt;: Reading something interesting/disgusting? Right click the mouse on the page and throw in a keyword, which is then stored in an indexing machine (may well be from Yahoo or Google) together with the URL. On the back of this, the index machine scan and sort the tag with other tags that already add to this article (URL) and apply some smart algorithm… &lt;/p&gt;&lt;br /&gt;Technorati Tags: &lt;a href="http://technorati.com/tag/Web2.0" rel="tag"&gt;Web 2.0&lt;/a&gt; &lt;a href="http://technorati.com/tag/Google+Yahoo" rel="tag"&gt;Google Yahoo&lt;/a&gt; &lt;a href="http://technorati.com/tag/Intention+Base+Search" rel="tag"&gt;Intention Base Search&lt;/a&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-115482169773208149?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/115482169773208149'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/115482169773208149'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2006/08/google-10-vs-yahoo-20.html' title='Google 1.0 vs Yahoo 2.0'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-115481919737422618</id><published>2006-08-06T00:06:00.000+01:00</published><updated>2006-08-06T00:06:37.403+01:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='web 2.0'/><title type='text'>Content or intention?</title><content type='html'>&lt;span id="BlogViewId"&gt;&lt;span style="font-style: italic;"&gt;How does the news industry "cross the chasm" and survive in a search-driven world? I don't have a silver bullet, unfortunately, but it starts by opening up its sites and realizing that in a post-Web world, the model for news is no longer site driven. Sites that wall themselves off are becoming irrelevant, not because the writing or analysis is necessarily flawed, but rather because their business model is. In today's ecosystem of news, the greatest sin is to cut one-self off from the conversation. Both The Economist and the Wall Street Journal have done just that&lt;br /&gt;...&lt;br /&gt;&lt;/span&gt;Remarking how traditional subscription based online media would be benefit from open up deep linking - allowing search and linking to their walled assert - subscription protected content:&lt;br /&gt;&lt;br /&gt;&lt;span style="font-style: italic;"&gt; The goal is to make content that is &lt;/span&gt;&lt;span style="font-weight: bold;"&gt;worth pointing to&lt;/span&gt;&lt;span style="font-style: italic;"&gt;. If you're feeding the conversation, the rest will then follow, including advertisers who want to be in the conversation that news stories are fostering. &lt;br /&gt;&lt;br /&gt;from &lt;a href="http://www.amazon.co.uk/gp/product/1857883616/"&gt;The Search&lt;/a&gt;, John Battelle&lt;/span&gt;&lt;/span&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-115481919737422618?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/115481919737422618'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/115481919737422618'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2006/08/content-or-intention.html' title='Content or intention?'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-115438148493477176</id><published>2006-07-31T22:26:00.000+01:00</published><updated>2006-07-31T22:31:24.940+01:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='not work'/><title type='text'>Too hot</title><content type='html'>&lt;style type="text/css"&gt;.flickr-photo { border: solid 2px #000000; }.flickr-yourcomment { }.flickr-frame { text-align: left; padding: 3px; }.flickr-caption { font-size: 0.8em; margin-top: 0px; }&lt;/style&gt;&lt;div class="flickr-frame"&gt; &lt;a href="http://www.flickr.com/photos/66168794@N00/203222260/" title="photo sharing"&gt;&lt;img src="http://static.flickr.com/63/203222260_5e618a168c.jpg" class="flickr-photo" alt="" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;span class="flickr-caption"&gt;&lt;a href="http://www.flickr.com/photos/66168794@N00/203222260/"&gt;Too hot&lt;/a&gt;, originally uploaded by &lt;a href="http://www.flickr.com/people/66168794@N00/"&gt;shortcutexplorer&lt;/a&gt;.&lt;/span&gt;&lt;/div&gt;    &lt;p class="flickr-yourcomment"&gt; You know it is too hot when an laptop battery needs a cool down like this&lt;/p&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-115438148493477176?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/115438148493477176'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/115438148493477176'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2006/07/too-hot.html' title='Too hot'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-115065726207657136</id><published>2006-06-18T20:01:00.000+01:00</published><updated>2006-06-18T20:01:02.146+01:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='vs.net'/><category scheme='http://www.blogger.com/atom/ns#' term='tdd'/><category scheme='http://www.blogger.com/atom/ns#' term='nunit'/><title type='text'>TDD Moving from 1.1 to 2.0</title><content type='html'>Moving dev environement to VS 2005, which by default targets .Net framework 2.0. To make it targets 1.1 here is &lt;a href="http://blogs.msdn.com/jomo_fisher/archive/2005/04/22/410903.aspx"&gt;Jomo Fisher : Hack the Build: Use Whidbey Beta2 to target .NET Runtime 1.1&lt;/a&gt;, which works on VS 2005 full release as well.&lt;br /&gt;I organise test assembly into a project within the same solution. It is quit cool to have differnt project configured to different .net framework versions.&lt;br /&gt;So the class library(test target) is 2.0 while test fixture is 1.1, which statisfies nUnit console (2.2.0). Soon I run into chicken and egg problem  - test asm reference test target - 1.1 on 2.0. Reverese dependency simply doesn't work.&lt;br /&gt;Luckily folks at nUnit.org didn't stop at when MS recuit one of their top guy and build a MS Unit Test into their VS Team Sytem. (I tried it in a few ocassion - awful I say).&lt;br /&gt;Quickly upgraded nUnit to 2.2.8 for .Net 2.0, put test asm back to 2.0. It works fine!&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-115065726207657136?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='related' href='http://blogs.msdn.com/jomo_fisher/archive/2005/04/22/410903.aspx' title='TDD Moving from 1.1 to 2.0'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/115065726207657136'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/115065726207657136'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2006/06/tdd-moving-from-11-to-20.html' title='TDD Moving from 1.1 to 2.0'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-114959663659206736</id><published>2006-06-06T13:23:00.000+01:00</published><updated>2006-06-06T13:23:56.710+01:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='win server'/><title type='text'>How to perform a clean boot in Windows XP</title><content type='html'>Over time, my computer getting slower on starting up. Happen to find this command MSConfig to the rescue.&lt;br /&gt;&lt;br /&gt;&lt;a href="http://support.microsoft.com/kb/310353/"&gt;How to perform a clean boot in Windows XP&lt;/a&gt;: "How to perform a clean boot in Windows XP&lt;br /&gt;Note You must be logged on as an administrator or a member of the Administrators group to follow these steps. If your computer is connected to a network, network policy settings may also prevent you from follow these steps. 1.Click Start, click Run, type msconfig in the Open box, and then click OK.&lt;br /&gt;2.On the General tab, click Selective Startup, and then clear the Process System.ini File, Process WIn.ini File, and Load Startup Items check boxes. You cannot clear the Use Original Boot.ini check box.&lt;br /&gt;3.On the Services tab, select the Hide All Microsoft Services check box, and then click Disable All.&lt;br /&gt;4.Click OK, and then click Restart to restart your computer.&lt;br /&gt;5.After Windows starts, determine whether the symptoms still occur.&lt;br /&gt;&lt;br /&gt;Note Look closely at the General tab to make sure that the check boxes that you cleared are still cleared. Continue to step 6 if none of the check boxes are selected. If the Load System Services check box is the only disabled check box, your computer is not clean-booted. If additional check boxes are disabled and the issue is not resolved, you may require help from the manufacturer of the program that places a check mark back in Msconfig.&lt;br /&gt;&lt;br /&gt;If none of the check boxes are selected, and the issue is not resolved, you may have to repeat steps 1 through 5, but you may also have to clear the Load System Services check box on the General tab. This temporarily disables Microsoft services (such as, Networking, Plug and Play, Event Logging, and Error Reporting) and permanently deletes all restore points for the System Restore utility. Do not do this if you want to retain your restore points for System Restore or if you must use a Microsoft service to test the issue.&lt;br /&gt;6.Click Start, click Run, type msconfig in the Open box"&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-114959663659206736?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='related' href='http://support.microsoft.com/kb/310353/' title='How to perform a clean boot in Windows XP'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/114959663659206736'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/114959663659206736'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2006/06/how-to-perform-clean-boot-in-windows.html' title='How to perform a clean boot in Windows XP'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-113939348023603082</id><published>2006-02-08T10:11:00.000Z</published><updated>2006-02-08T10:11:20.306Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='win server'/><title type='text'>Stealth Server (DNS)</title><content type='html'>Chapter 1. Introduction:&lt;em&gt; "You can list servers in the zone's top-level NS records that are not in the parent's NS delegation, but you cannot list servers in the parent's delegation that are not present at the zone's top level."&lt;/em&gt;&lt;br /&gt;&lt;br /&gt;- the beauty of flawless logic and phrase.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-113939348023603082?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='related' href='http://www.isc.org/index.pl?/sw/bind/' title='Stealth Server (DNS)'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/113939348023603082'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/113939348023603082'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2006/02/stealth-server-dns.html' title='Stealth Server (DNS)'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-113344196407660786</id><published>2005-12-01T12:59:00.000Z</published><updated>2006-11-01T12:00:54.452Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='sql'/><category scheme='http://www.blogger.com/atom/ns#' term='xml'/><title type='text'>Don't mix ExecuteScalar  with For XML EXPLICIT</title><content type='html'>In doing SQL Server data retrieval, it is very handy to issue a ‘For XML EXPLICIT’ Select query in the stored procedure. Then in the DB application code use ExecuteScalar to read it.&lt;br /&gt;&lt;br /&gt;So far so good – until recently - I decide to increase a char field length by 10 bytes. Suddenly a few unit test cases break (thanks God, they break…). Return Xml string is truncated at 2033 characters.&lt;br /&gt;&lt;br /&gt;This behaviour occurs because, for XML results greater than 2,033 characters in length, SQL Server returns the XML in multiple rows of 2,033 characters each.&lt;br /&gt;&lt;br /&gt;This &lt;a href="http://www.aspnetresources.com/blog/executescalar_truncates_xml.aspx"&gt;article&lt;/a&gt;&lt;br /&gt;ASP.NET Resources - ExecuteScalar Truncates XML at 2,033 Characters investigates and describes the symptom in detail.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-113344196407660786?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='related' href='http://www.aspnetresources.com/blog/executescalar_truncates_xml.aspx' title='Don&apos;t mix ExecuteScalar  with For XML EXPLICIT'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/113344196407660786'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/113344196407660786'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2005/12/dont-mix-executescalar-with-for-xml.html' title='Don&apos;t mix ExecuteScalar  with For XML EXPLICIT'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-113223267778260806</id><published>2005-11-17T13:02:00.000Z</published><updated>2005-11-17T13:04:37.793Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='not work'/><title type='text'>Unleash the power of the people</title><content type='html'>Small teams with orthogonal tasks is better than a larger team where everyone trying to/not to stand in other's way.&lt;br /&gt;&lt;br /&gt;By orthogonal (a mathematics term) I mean a well defined responsibility: Everyone knows what he/she is or supposed to do;&lt;br /&gt;Everyone knows what other would expect him/her to deliver at certain time;&lt;br /&gt;Everyone knows what he/she could rely on other to deliver to get his/her work done at agreed time.&lt;br /&gt;&lt;br /&gt;I am talking in terms of engineering (e.g. software)&lt;br /&gt;In this context, small team incurs less overhead to reach same level of communication effort that larger team need.&lt;br /&gt;&lt;br /&gt;A big thanks to Rob Styles!&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-113223267778260806?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/113223267778260806/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=113223267778260806' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/113223267778260806'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/113223267778260806'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2005/11/unleash-power-of-people.html' title='Unleash the power of the people'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-263467326475844795</id><published>2005-11-05T11:54:00.000Z</published><updated>2006-11-12T13:09:39.151Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='.net'/><title type='text'>Determistic Finalization with IDisposable</title><content type='html'>&lt;span style="font-weight: bold;"&gt;Finalization, how it works?&lt;/span&gt;&lt;br /&gt;Heap exhaustion/shutting down an application triggers a Garbage Collection. Class that manage external resources like DB connection, file handler should implement Finalization to improve the system performance – proactively release the (external) resource once finished use.&lt;br /&gt;&lt;br /&gt;However, objects that require finalization complicate the collection process. An object with a finalizer is  not immediately released. How is works? GC checks metadata of every object type in the scan. If the object implements the &lt;span style="font-family:courier new;"&gt;Finalize()&lt;/span&gt; method, GC doesn't destroy it. Instead it is marked as reachable and it moved from it's orginal graph to another object graph- a special queue called &lt;span style="font-style: italic;"&gt;finalized  queue&lt;/span&gt;, which establishes a reference to the object, preventing its collection. GC proceeds. Meanwhile, a seperate background thread iterates all objects in the &lt;span style="font-style: italic;"&gt;finalized  queue,&lt;/span&gt; calling Finalize() on each and removes the finalized object from the finalization queue.&lt;br /&gt;&lt;br /&gt;There is a fair standard pattern on implementing Finalize, such like define it as proteced+virtual; calling parent's Finalize at the end of your call... In fact c# comes with a code template destructor (~{MyClassName}), compiler expands it to full size &lt;span style="font-family:courier new;"&gt;Finalize()&lt;/span&gt; method at compiling.&lt;br /&gt;&lt;br /&gt;Only after finalization can the object be removed from memory during the *next* GC pass. As a side effect of surviving one collection pass, the object is promoted into a higher generation, further delaying its eventual collection-&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;Non-Determistic Finalization&lt;/span&gt; meaning Garbage collection time is unpreditable. The application  should not rely on GC to clean up expensive resources, which hurts scalability and performance.&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;Determistic Finalization&lt;/span&gt;&lt;br /&gt;&lt;span&gt;To free up used resources, client should proactively release used resource, such like DB connection when it is no longer used, instead of relies on GC.&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style="font-weight: bold;"&gt;&lt;br /&gt;-The Open()/Close() Pattern&lt;br /&gt;&lt;/span&gt;Use object pool to manage objects without really destroy an object. Many .Net framwork classes use this pattern, E.g. file, stream (I/O, memory, network), DB connection, communication port etc.&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;-&lt;/span&gt;&lt;span style="font-weight: bold;font-family:courier new;" &gt;IDisposable&lt;/span&gt;&lt;span style="font-weight: bold;"&gt; Pattern&lt;/span&gt;&lt;span style="font-weight: bold;"&gt;&lt;/span&gt;&lt;br /&gt;Classes that require finalization should implement the &lt;span style="font-weight: bold;font-family:courier new;" &gt;IDisposable &lt;/span&gt;interface in order to allow client to provide a determistic finalisatoin - short-circuit GC finalization and avoid the garbaged object (which uses external resource, say) promoted to G1.&lt;br /&gt;There are two ways that classes that implement IDisposable have their objects being cleaned up.&lt;br /&gt;&lt;br /&gt;1) Client code explicitly calls &lt;span style="font-weight: bold;font-family:courier new;" &gt;Dispose&lt;/span&gt;&lt;span style="font-family:courier new;"&gt;. &lt;/span&gt;&lt;br /&gt;Your implementation in Dispose has the _chance_ to explicitly clean-up unmanaged resource as well as managed resource (by GC). By now your unmanaged resource is already freed up, there is no point to put the object in &lt;span style="font-style: italic;"&gt;finalize queue&lt;/span&gt; to delays its release (G1), you should supress this by calling &lt;span&gt;&lt;span style="font-size:78%;"&gt;GC.SuppressFinalize(this);&lt;br /&gt;&lt;br /&gt;&lt;/span&gt;&lt;/span&gt;2) Destructor &lt;span style="font-weight: bold;font-family:courier new;" &gt;Finalize &lt;/span&gt;method calls &lt;span style="font-weight: bold;font-family:courier new;" &gt;Dispose.&lt;/span&gt; This is a fallback plan if client fails to clean up.&lt;span style="font-weight: bold;font-family:courier new;" &gt; &lt;/span&gt;&lt;br /&gt;In this case the &lt;span style="font-weight: bold;font-family:courier new;" &gt;Dispose &lt;/span&gt;method can only clean up unmanaged resource. Because during finalization, GC may have already removed the object for which &lt;span style="font-weight: bold;font-family:courier new;" &gt;Dispose &lt;/span&gt;is called (in following code example, the timer object). In this case, &lt;span style="font-weight: bold;font-family:courier new;" &gt;Dispose &lt;/span&gt;calls to clean this object, it will fail on null referencing.&lt;br /&gt;&lt;br /&gt;Sample code from MCSD training material:&lt;br /&gt;&lt;pre  style="color: rgb(102, 102, 102);font-family:courier new;" class="codebody"&gt;&lt;span style="font-size:78%;"&gt;// Implementing IDisposable implies that the&lt;br /&gt;// instances of this class will use unmanaged resources&lt;br /&gt;&lt;br /&gt;public class Parent:IDisposable&lt;br /&gt;{&lt;br /&gt;  // An unmanaged resource&lt;br /&gt;  private IntPtr ptr;&lt;br /&gt;&lt;br /&gt;  // A Managed resource&lt;br /&gt;  private System.Timers.Timer  timer;&lt;br /&gt;&lt;br /&gt;  // Variable to track call to Dispose method&lt;br /&gt;  private bool disposed;&lt;br /&gt;&lt;br /&gt;  public Parent()&lt;br /&gt;  {&lt;br /&gt;      // Implement constructor     &lt;br /&gt;  }&lt;br /&gt;&lt;br /&gt;  public void Dispose()&lt;br /&gt;  {&lt;br /&gt;      // Call the overloaded Dispose method&lt;br /&gt;      // with true as argument, indicating that&lt;br /&gt;      // Dispose is called by the user of the object&lt;br /&gt;      Dispose(true);&lt;br /&gt;      // Suppress the Finalize method so that it does not call Dispose again&lt;br /&gt;      GC.SuppressFinalize(this);&lt;br /&gt;  }&lt;br /&gt;&lt;br /&gt;  protected virtual void Dispose(bool called_by_user )&lt;br /&gt;  {&lt;br /&gt;      if  (!this.disposed)&lt;br /&gt;      {&lt;br /&gt;          // if the user of the object called the Dispose method&lt;br /&gt;          // Clean managed as well as unmanaged data&lt;br /&gt;          // Otherwise clean only unmanaged data&lt;br /&gt;          if (called_by_user)&lt;br /&gt;          {&lt;br /&gt;              // Clean managed data&lt;br /&gt;              timer.Dispose();&lt;br /&gt;          }&lt;br /&gt;          ptr = IntPtr.Zero;&lt;br /&gt;          disposed = true;&lt;br /&gt;      }&lt;br /&gt;      //base.Dispose();&lt;br /&gt;  }&lt;br /&gt;  // C# destructor which is used to execute the finalization code&lt;br /&gt;  ~Parent()&lt;br /&gt;  {&lt;br /&gt;      Dispose(false);&lt;br /&gt;  }&lt;br /&gt;&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;public class Child:Parent&lt;br /&gt;{.&lt;br /&gt;.&lt;br /&gt;.&lt;br /&gt;&lt;br /&gt;  protected override void Dispose(bool called_by_user )&lt;br /&gt;  {&lt;br /&gt;      // Cleanup code for the child object&lt;br /&gt;      .&lt;br /&gt;      .&lt;br /&gt;      .&lt;br /&gt;&lt;br /&gt;      // Call Dispose method of the Parent class&lt;br /&gt;      base.Dispose(called_by_user);&lt;br /&gt;&lt;br /&gt;  }&lt;br /&gt;}&lt;br /&gt;&lt;/span&gt;&lt;/pre&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-263467326475844795?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/263467326475844795'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/263467326475844795'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2005/11/gc-idisposable.html' title='Determistic Finalization with IDisposable'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-113101227722397103</id><published>2005-11-03T10:04:00.000Z</published><updated>2005-11-03T10:07:15.670Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='not work'/><title type='text'>I am as good as Chris Sells in Math</title><content type='html'>&lt;table align="center" border="0" cellpadding="2" cellspacing="0" width="350"&gt;&lt;tbody&gt;&lt;tr&gt;&lt;td align="center" bg style="color:#cddeff;"&gt;&lt;span style="color: black; font-size: 14pt;font-family:Georgia, Times New Roman, Times, serif;" &gt;&lt;b&gt;You Passed 8th Grade Math&lt;/b&gt;&lt;/span&gt;&lt;/td&gt;&lt;/tr&gt;&lt;tr&gt;&lt;td bgcolor="#ebf2ff"&gt;&lt;center&gt;&lt;img src="http://images.blogthings.com/couldyoupasseighthgrademathquiz/passed.jpg" height="100" width="100" /&gt;&lt;/center&gt;&lt;span style="color:#000000;"&gt;&lt;br /&gt;Congratulations, you got 9/10 correct!&lt;/span&gt;&lt;/td&gt;&lt;/tr&gt;&lt;/tbody&gt;&lt;/table&gt;&lt;div align="center"&gt;&lt;a href="http://www.blogthings.com/couldyoupasseighthgrademathquiz/"&gt;Could You Pass 8th Grade Math?&lt;/a&gt;&lt;/div&gt;&lt;br /&gt;&lt;br /&gt;Chris's result &lt;a href="http://www.sellsbrothers.com/news/showTopic.aspx?ixTopic=1891"&gt;here &lt;/a&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-113101227722397103?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='related' href='http://www.sellsbrothers.com/news/showTopic.aspx?ixTopic=1891' title='I am as good as Chris Sells in Math'/><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/113101227722397103/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=113101227722397103' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/113101227722397103'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/113101227722397103'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2005/11/i-am-as-good-as-chris-sells-in-math.html' title='I am as good as Chris Sells in Math'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-113044851279387176</id><published>2005-10-27T22:27:00.000+01:00</published><updated>2005-10-27T22:28:32.806+01:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='vs.net'/><category scheme='http://www.blogger.com/atom/ns#' term='tdd'/><title type='text'>Anti Intellisense with Test Driven Development</title><content type='html'>&lt;em&gt;"I don’t think IntelliSense[note 1] is helping us become better programmers. The real objective is for us to become faster programmers, which also means that it’s cheapening our labor. "&lt;/em&gt; -- Charles Petzold &lt;a href="http://charlespetzold.com/etc/DoesVisualStudioRotTheMind.html"&gt;A Talk Delivered at the NYC .NET Developer’s Group, October 20, 2005&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;I have to agree with Charles that Intellisense changes the way we code, it turns design and implementation solution to be kindof conversation with development environment and hence slave to it.&lt;br /&gt;&lt;br /&gt;Luckily, here comes rescue: Test Driven Development. With it you can actually start your implementation with the requirement, demand and the burning need to fix the broken test case. You actually start with a question 'what do I want to achieve by doing this?' You then start with using a method, a member variable before had it defined. And with Re-Sharper, you can easily turn the undeclared member into a skeleton you can implement later.&lt;br /&gt;&lt;br /&gt;Because they are undeclared when first used, Intellisense won't pop up.&lt;br /&gt;&lt;br /&gt;Hurray!&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-113044851279387176?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/113044851279387176/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=113044851279387176' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/113044851279387176'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/113044851279387176'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2005/10/anti-intellisense-with-test-driven.html' title='Anti Intellisense with Test Driven Development'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-113041281160261749</id><published>2005-10-27T12:29:00.000+01:00</published><updated>2005-10-27T12:33:31.613+01:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='object'/><title type='text'>Object Invocation Earliy binding vs Late binding</title><content type='html'>&lt;a href="http://photos1.blogger.com/blogger/4798/282/1600/stree.jpg"&gt;&lt;img style="margin: 0pt 0pt 10px 10px; float: right; cursor: pointer;" src="http://photos1.blogger.com/blogger/4798/282/320/stree.jpg" alt="" border="0" /&gt;&lt;/a&gt;&lt;br /&gt;1) Use early binding – so the types are known at compile time.&lt;br /&gt;&lt;br /&gt;2) Use Remoting Activator – under the hood, it is Reflection&lt;br /&gt;&lt;br /&gt;&lt;div class="code"&gt;&lt;br /&gt;//caller&lt;br /&gt;Object instance = CreateInstanceUseReflection(myType, newArgs);&lt;br /&gt;… …&lt;br /&gt; private object CreateInstanceUseReflection(Type type, object[] args)&lt;br /&gt; {&lt;br /&gt;  object instance = type.InvokeMember("",&lt;br /&gt;   BindingFlags.CreateInstance | BindingFlags.Public | BindingFlags.Instance,&lt;br /&gt;   null,&lt;br /&gt;   null,&lt;br /&gt;   args);&lt;br /&gt;  return instance;&lt;br /&gt; }&lt;br /&gt;&lt;/div&gt;&lt;br /&gt;3) Use Reflection directly&lt;br /&gt;&lt;div class="code"&gt;&lt;br /&gt;//caller&lt;br /&gt;Object instance = CreateInstanceUseRemoting(myType, newArgs);&lt;br /&gt; … …&lt;br /&gt;private object CreateInstanceUseRemoting(Type type, object[] args)&lt;br /&gt; {&lt;br /&gt;  return Activator.CreateInstance(type, args);&lt;br /&gt;}&lt;br /&gt;&lt;/div&gt;&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;The test&lt;/strong&gt;&lt;br /&gt;&lt;br /&gt;I stress it will a search on 10,000 records against a 2 million records DB. And here is the result: (in milliseconds; timing on average of three runs each.)&lt;br /&gt;&lt;br /&gt;use Remoting Activator 33855.69480   &lt;br /&gt;use Reflection 33422.52055   &lt;br /&gt;use Early Binding 31251.81840&lt;br /&gt;&lt;br /&gt;Interesting to know.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-113041281160261749?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/113041281160261749/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=113041281160261749' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/113041281160261749'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/113041281160261749'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2005/10/object-invocation-earliy-binding-vs.html' title='Object Invocation Earliy binding vs Late binding'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-113027267441954347</id><published>2005-10-25T21:35:00.000+01:00</published><updated>2006-11-01T12:00:07.964Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='.net'/><category scheme='http://www.blogger.com/atom/ns#' term='xml'/><title type='text'>Lesson learnt: Implement IXmlSerializable to override Wsdl definition (Part II)</title><content type='html'>It is fine to override &lt;span class="codesnippet"&gt;IXmlSerializable&lt;/span&gt; if you only intend to use XmlSerializer. If you want to generate web service wsdl definition as well, there is a problem. Our http://MyNamespace.Jingye.com/SomeWebService.asmx?wsdl gives you something like this:&lt;br /&gt;&lt;div class="code"&gt;&lt;br /&gt;&amp;lt;s:element minOccurs="0" maxOccurs="unbounded" name="Foo"&amp;gt;&lt;br /&gt;&amp;lt;s:complexType&amp;gt;&lt;br /&gt;&amp;lt;s:sequence&amp;gt;&lt;br /&gt;&amp;lt;s:any namespace="http://mynamespace.jingye.com /Foo" /&amp;gt;&lt;br /&gt;&amp;lt;/s:sequence&amp;gt;&lt;br /&gt;&amp;lt;/s:complexType&amp;gt;&lt;br /&gt;&amp;lt;/s:element&amp;gt;&lt;br /&gt;…&lt;br /&gt;&lt;br /&gt;&amp;lt;s:schema xmlns:xs="http://www.w3.org/2001/XMLSchema" elementFormDefault="qualified" targetNamespace=" http://mynamespace.jingye.com" id="Foo"&amp;gt;&lt;br /&gt;&amp;lt;xs:element name="Foo"&amp;gt;&lt;br /&gt;&amp;lt;xs:complexType&amp;gt;&lt;br /&gt;&amp;lt;xs:sequence&amp;gt;&lt;br /&gt;&amp;lt;xs:element name="MemberVar" type="xs:string" /&amp;gt;&lt;br /&gt;&amp;lt;/xs:sequence&amp;gt;&lt;br /&gt;&amp;lt;/xs:complexType&amp;gt;&lt;br /&gt;&amp;lt;/xs:element&amp;gt;&lt;br /&gt;&amp;lt;/s:schema&amp;gt;&lt;br /&gt;&lt;/div&gt;&lt;br /&gt;Although look like we have the schema definition for Foo and would be able to use it to validate a Foo object and provide type info for de-serialisation. It is not. Any short-circuits our wsdl tool to combine external and internal schemas into one service description. If the message object is of a different XML namespace than the service, duplicate schema information is generated in the subsequent WSDL file (one for the correct XML namespace, and one for the service). If your message object is of the same XML namespace as the service, then the WSDL generation fails because the document can't contain the same namespace twice. In either of these cases, you do not get the behaviour that you are looking for. Article &lt;a href="http://msdn.microsoft.com/msdnmag/issues/05/03/WSE20/default.aspx"&gt;WSE 2.0: Give Your Web Services Consumers the Exact XML They Need to Succeed&lt;/a&gt; explains this.&lt;br /&gt;&lt;br /&gt;It seemed that .NET Framework 2.0, this problem is solved by allowing the object to return an element of a schema instead of an entire schema document, which makes it possible to merge schemas during the WSDL generation step. Read this &lt;a href="http://msdn.microsoft.com/library/default.asp?url=/library/en-us/dnvs05/html/wsnetfx2.asp"&gt;"New Features for Web Service Developers in Beta 1 of the .NET Framework 2.0"&lt;/a&gt;.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-113027267441954347?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/113027267441954347/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=113027267441954347' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/113027267441954347'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/113027267441954347'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2005/10/lesson-learnt-implement_25.html' title='Lesson learnt: Implement IXmlSerializable to override Wsdl definition (Part II)'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-113016294397440557</id><published>2005-10-24T21:40:00.000+01:00</published><updated>2006-11-01T12:00:27.879Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='.net'/><category scheme='http://www.blogger.com/atom/ns#' term='xml'/><title type='text'>Lesson learnt:  Implement IXmlSerializable to override Wsdl definition (Part I)</title><content type='html'>This is part one of implementing IXmlSerializable to customised object serialization.&lt;br /&gt;&lt;br /&gt;Overriding WSDl definition is easy. You just need to implement &lt;span class="codesnippet"&gt;IXmlSerializable&lt;/span&gt; for your type definition. &lt;span class="codesnippet"&gt;IXmlSerializable&lt;/span&gt; contains three methods that is used by wsdl serialisation.&lt;br /&gt;&lt;span class="codesnippet"&gt;GetSechma&lt;/span&gt;: Implement this method to supply our custom schema definition.&lt;br /&gt;&lt;span class="codesnippet"&gt;WriteXml&lt;/span&gt;: Implement this method to write xml fragment&lt;br /&gt;&lt;span class="codesnippet"&gt;ReadXml&lt;/span&gt;: Tells your object how to de-serialise xml doc into an object of this type.&lt;br /&gt;&lt;br /&gt;Here is a sample:&lt;br /&gt;&lt;div class="Code"&gt;&lt;br /&gt;public class Foo: IXmlSerializable&lt;br /&gt;{&lt;br /&gt;private string _memberVar;&lt;br /&gt;&lt;br /&gt;/// &lt;summary&gt;default constructor used by XmlSerializer&lt;/summary&gt;&lt;br /&gt;public Foo(){ }&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;XmlSchema IXmlSerializable.GetSchema()&lt;br /&gt;{&lt;br /&gt; Stream s = null;&lt;br /&gt; try&lt;br /&gt; {&lt;br /&gt;  s = base.GetSchema(typeof (Foo), "Foo.xsd");&lt;br /&gt;  s.Position = 0;&lt;br /&gt;  s.Flush();&lt;br /&gt;  XmlSchema schema = XmlSchema.Read(s, null);&lt;br /&gt;  schema.Compile(null);&lt;br /&gt;  return schema;&lt;br /&gt; }finally&lt;br /&gt; {&lt;br /&gt;  s.Close();&lt;br /&gt; }&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;//   ... if use default behaviour for serialization&lt;br /&gt;//              [XmlElement("MemberVar")]&lt;br /&gt;//  public String MemberVar&lt;br /&gt;//  {&lt;br /&gt;//   get {return _memberVar;}&lt;br /&gt;//   set { //serializer requires this }&lt;br /&gt;//  }&lt;br /&gt;&lt;br /&gt;/// &lt;summary&gt;we do not implement this method because we only intend to use it for serialisation (from object to xml data)&lt;/summary&gt;&lt;br /&gt;void IXmlSerializable.ReadXml(XmlReader reader)&lt;br /&gt;{&lt;br /&gt; throw new NotImplementedException();&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;void IXmlSerializable.WriteXml(XmlWriter writer)&lt;br /&gt;{&lt;br /&gt; //&lt;foo&gt;&lt;br /&gt; // &lt;membervar&gt;dwiohfjwhfjekfhjsdkhf&lt;/membervar&gt;&lt;br /&gt; //&lt;/foo&gt;&lt;br /&gt;&lt;br /&gt; // Do somthing to load _membervar?&lt;br /&gt; writer.WriteElementString("MemberVa", _memberVar);&lt;br /&gt;&lt;br /&gt; //WARNING: Don't close the writer here! Let serilizer do it for you!!!&lt;br /&gt; //writer.Close();&lt;br /&gt;}&lt;br /&gt;}&lt;br /&gt;}&lt;br /&gt;&lt;/div&gt;&lt;br /&gt;&lt;br /&gt;Foo.xsd is supplied as an embedded resource:&lt;br /&gt;&lt;div class="code"&gt;&lt;br /&gt;&amp;lt;xs:schema id="Foo" targetNamespace="http://mynamespace.jingye.com" xmlns:xs="http://www.w3.org/2001/XMLSchema"  elementFormDefault="qualified"&amp;gt;&lt;br /&gt;&amp;lt;xs:element name="Foo"&amp;gt;&lt;br /&gt;&amp;lt;xs:complexType&amp;gt;&lt;br /&gt;&amp;lt;xs:sequence&amp;gt;&lt;br /&gt; &amp;lt;xs:element name="MemberVar" type="xs:string" /&amp;gt;&lt;br /&gt;&amp;lt;/xs:sequence&amp;gt;&lt;br /&gt;&amp;lt;/xs:complexType&amp;gt;&lt;br /&gt;&amp;lt;/xs:element&amp;gt;&lt;br /&gt;&amp;lt;/xs:schema&amp;gt;&lt;br /&gt;&lt;/div&gt;&lt;br /&gt;This would serialize a Foo object to:&lt;br /&gt;&lt;div class="Code"&gt;&lt;br /&gt;&amp;lt;Foo&amp;gt;MemberVar&amp;gt;Some Data&amp;lt;/MemberVar&amp;gt;l&amp;lt;/Foo&amp;gt;&lt;br /&gt;&lt;/div&gt;&lt;br /&gt;And the parent element (Say ‘Bar’) of Type Foo could have WriteXml like this&lt;br /&gt;&lt;div class="Code"&gt;&lt;br /&gt;public class Bar : IXmlSerializable&lt;br /&gt;{&lt;br /&gt;public Foo[] Item;&lt;br /&gt;        ...&lt;br /&gt;public void WriteXml(XmlWriter writer)&lt;br /&gt;{&lt;br /&gt; foreach (Foo r in Item)&lt;br /&gt; {&lt;br /&gt;  writer.WriteStartElement("Foo");&lt;br /&gt;  ((IXmlSerializable)r).WriteXml(writer);&lt;br /&gt;  writer.WriteEndElement();&lt;br /&gt; }&lt;br /&gt;}&lt;br /&gt;&lt;/div&gt;&lt;br /&gt;This would serialize a Bar object to:&lt;br /&gt;&lt;div class="Code"&gt;&lt;br /&gt;&amp;lt;Bar&amp;gt;&lt;br /&gt;&amp;lt;Foo&amp;gt;&amp;lt;MemberVar&amp;gt;Some Data 1&amp;lt;/MemberVar&amp;gt;&amp;lt;/Foo&amp;gt;&lt;br /&gt;&amp;lt;Foo&amp;gt;&amp;lt;MemberVar&amp;gt;Some Data 2&amp;lt;/MemberVar&amp;gt;&amp;lt;/Foo&amp;gt;&lt;br /&gt;&amp;lt;/Bar&amp;gt;&lt;br /&gt;&lt;/div&gt;&lt;br /&gt;&lt;br /&gt;So when does serialisation happen, when WriteXml and ReadXml gets called?&lt;br /&gt;&lt;br /&gt;WriteXml is called when XmlSerializer is to marshal an object, you can verify this by knock off a quick (nunit) test case like this:&lt;br /&gt;&lt;div class="code"&gt;&lt;br /&gt;[Test]public void Test()&lt;br /&gt;{&lt;br /&gt;&lt;br /&gt; XmlDocument expectedXml = new XmlDocument();&lt;br /&gt; //Build your expected result&lt;br /&gt; ///...&lt;br /&gt;&lt;br /&gt; Foo aFoo = new Foo(...);  //if your constructor takes param to initialize memberVar&lt;br /&gt;&lt;br /&gt; XmlSerializer xs = new XmlSerializer(typeof (Foo));&lt;br /&gt;&lt;br /&gt; xtwriter.Formatting = Formatting.None;&lt;br /&gt;&lt;br /&gt;&lt;br /&gt; // WriteXml() is called here&lt;br /&gt; xs.Serialize(xtwriter, aFoo);&lt;br /&gt;&lt;br /&gt; XmlDocument doc = new XmlDocument();&lt;br /&gt; xtwriter.Flush();&lt;br /&gt; ms.Position = 0;&lt;br /&gt; ms.Flush();&lt;br /&gt; doc.Load(ms);&lt;br /&gt;&lt;br /&gt; Assert.AreEqual(expectedXml.OuterXml, doc.OuterXml);&lt;br /&gt;}&lt;br /&gt;&lt;/div&gt;&lt;br /&gt;GetSchema is called when wsdl is invoked to generate the type definition. This could be using http://MyNamespace.Jingye.com/SomeWebService.asmx?wsdl or by using MS wsdl tool at command line to generate client proxy class.&lt;br /&gt;&lt;br /&gt;However, if you do either of that, and if you look carefully, you will see a problem. I will talk about it in the second part.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-113016294397440557?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/113016294397440557/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=113016294397440557' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/113016294397440557'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/113016294397440557'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2005/10/lesson-learnt-implement.html' title='Lesson learnt:  Implement IXmlSerializable to override Wsdl definition (Part I)'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-112858575424369677</id><published>2005-10-06T08:51:00.000+01:00</published><updated>2006-11-01T11:59:42.815Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='nant'/><title type='text'>Passing double/single quote in Nant task</title><content type='html'>Tasks like &lt;exec&gt; in Nant doesn't like nested quotes. If you want to pass a commandline argurement that contains double quotes (for space in directory names need double quotes around it), you will have small problem.&lt;br /&gt;For example, you cann't do this:&lt;br /&gt;&lt;/exec&gt;&lt;div id="nantquote1" class="code"&gt;&lt;br /&gt;&amp;lt;exec workingdir="c:workingdir\bin" basedir="c:\executableDir" program="sar.exe" commandline="/s:ContentDB.config /d:..\..\ContentDB.config /f:&lt;strong&gt;"&lt;/strong&gt;my file contains space&lt;strong&gt;"&lt;/strong&gt; /i" /&amp;gt;&lt;br /&gt;&lt;/div&gt;&lt;br /&gt;Have tried a few ways to escape the double quote, not very sucessful. Suddenly I find we can do this:&lt;br /&gt;1) add a property at top for double/single quote&lt;br /&gt;2) use it!&lt;br /&gt;&lt;div id="nantquote2" class="code"&gt;&lt;br /&gt;&amp;lt;property name="quote" value='"' /&amp;gt;&lt;br /&gt;...&lt;br /&gt;&amp;lt;exec workingdir="c:workingdir\bin" basedir="c:\executableDir" program="sar.exe" commandline="/s:ContentDB.config /d:..\..\ContentDB.config /f:&lt;strong&gt;${quote}&lt;/strong&gt;my file contains space&lt;strong&gt;${quote}&lt;/strong&gt; /i" /&amp;gt;&lt;br /&gt;&lt;/div&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-112858575424369677?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/112858575424369677/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=112858575424369677' title='1 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/112858575424369677'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/112858575424369677'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2005/10/passing-doublesingle-quote-in-nant.html' title='Passing double/single quote in Nant task'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><thr:total>1</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-112807835816671353</id><published>2005-09-30T12:05:00.000+01:00</published><updated>2006-11-01T12:02:14.054Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='nant'/><category scheme='http://www.blogger.com/atom/ns#' term='Continuous Integration'/><title type='text'>Control the host name/port ID when VS.Net or DevEnv load a web app</title><content type='html'>Stable build and integration build cannot host by a single machine. It is all due to when IIS and VS.NET creates a web app it always creates it in default location -  local host.&lt;br /&gt;&lt;br /&gt;The background:&lt;br /&gt;W2k3, IIS6, .NET, SQL Server&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;Prove it 1. using vs.net&lt;/strong&gt;&lt;br /&gt;&lt;br /&gt;Using vs.net to open a web app which is configured to run at port 8080, notice it complains cannot find the web app at localhost(80) and tries to create one.  I am sure you are familiar with the ‘smart way’ IIS and VS.net tries to recreate XXXXX_1 web app for you. Same thing here.&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;Prove it: 2 using DevEnv.exe&lt;/strong&gt;&lt;br /&gt;Here comes the long story:&lt;br /&gt;On the CI build server, two web apps (part of the solution; both set to vdir in IIS) is hosted by the default web app (localhost:80). This config works fine with CC.net and Nant. Web apps can be built and tested properly.&lt;br /&gt;&lt;br /&gt;Now on the same build server, I would like to have an independent nightly build process using CC.net.&lt;br /&gt;&lt;br /&gt;From file system, the entire nightly build solution is a sibling to the CI build solution.&lt;br /&gt;I create a new (IIS) Application pool – just to have a clean cut from the default application pool;&lt;br /&gt;I create a NightlyBuild web App in this App pool, and I config the two web apps to map to their directories in nightly build solution. So they are symmetrical to the CI build settings. And I assign port 8081 to NightlyBuild web app.&lt;br /&gt;&lt;br /&gt;Launch the Nant build process. Everything seemed worked fine. The build report actually says it. But when looking into the web apps. Source codes are fresh from source safe (check timestamp). However, there are no bin folders there. It looked like they are not built at all.&lt;br /&gt;&lt;br /&gt;Turn to the CI build solution, there are bin folders. Then look up binaries. I was expecting the timestamp being older – when they are lastly built. Hi Presto, it is the timestamp of NightlyBuild’s.&lt;br /&gt;&lt;br /&gt;See what I mean?&lt;br /&gt;&lt;br /&gt;When start VS.net IDE or use DevEnv. It will always try to register the web app in http://localhost(:80) without any exception.&lt;br /&gt;&lt;br /&gt;I wonder if there is a way I can intervene into this by Nant. So I can control the web app to be mapped to, say localhost:8080?&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-112807835816671353?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/112807835816671353/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=112807835816671353' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/112807835816671353'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/112807835816671353'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2005/09/control-host-nameport-id-when-vsnet-or.html' title='Control the host name/port ID when VS.Net or DevEnv load a web app'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-112739313921626947</id><published>2005-09-22T12:59:00.000+01:00</published><updated>2006-11-01T12:03:31.554Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='.net'/><category scheme='http://www.blogger.com/atom/ns#' term='xml'/><title type='text'>Loading Xml Serialization Object Graph</title><content type='html'>A memo on using XmlSerializer.Serialize and loading the object graph:&lt;br /&gt;1) use default XmlTextWriter&lt;br /&gt;2) provide StringWriter to control the xml output format&lt;br /&gt;3) use MemoryStream to control encoding&lt;br /&gt;4) by lazy, use Console.Out to check the output on screen&lt;br /&gt;&lt;br /&gt;There are quite a few ways to stream out the XmlSerializer marshalling result depends on the need.&lt;br /&gt;&lt;br /&gt;How XmlSerializer.Serialize works?&lt;br /&gt;&lt;div id="XmlSerializerStreamOutput1" class="code"&gt;&lt;br /&gt;1.  XmlSerializer xs = new XmlSerializer(typeof(Foo));&lt;br /&gt;2.  xs.Serialize(..., aFoo);&lt;br /&gt;&lt;/div&gt;&lt;br /&gt;On excuting the second line, our serializer then tries to serialize aFoo to Foo type. If Foo implements IXmlSerializable, it will ingore all public properties and just execute WriterXml that Foo implemented.&lt;br /&gt;By default, serializer passes an object of XmlTextWriter to WriterXml. In your WriterXml implementation, you should never close the Writer. This should be left to the caller (XmlSerializer in our case).&lt;br /&gt;&lt;br /&gt;How to serialize an object and load the marshalled result (object graph)?&lt;br /&gt;The most common way is use the default XmlTextWriter&lt;br /&gt;However, the xml document gererated is nicely formatted - i.e. indented. If a custom control over the format is needed, you need to passed your XmlTextWriter object to Serializer&lt;br /&gt;&lt;div id="XmlSerializerStreamOutput3" class="code"&gt;&lt;br /&gt;1.  XmlSerializer xs = new XmlSerializer(typeof(Foo));&lt;br /&gt;2.  using (StringWriter sw = new StringWriter())&lt;br /&gt;3.  {&lt;br /&gt;4.   XmlTextWriter xtwriter =new XmlTextWriter(sw);&lt;br /&gt;5.   xtwriter.Formatting = Formatting.None;&lt;br /&gt;6.   xs.Serialize(xtwriter, item.Reviews);&lt;br /&gt;7.   Console.WriteLine(sw.ToString());&lt;br /&gt;8.  }&lt;br /&gt;&lt;/div&gt;&lt;br /&gt;As seen, we have a control over on the xml doc layout by specified Formatting style.&lt;br /&gt;Not everthing can be controlled if use StringWriter though. It is Unicode base, so unless you &lt;a href="http://weblogs.asp.net/rmclaws/archive/2003/10/19/32534.aspx"&gt;override (or hijack?) StringWriter&lt;/a&gt;, you will always see utf-16 encoding&lt;br /&gt;&lt;span id="XmlSerializerStreamOutput1" class="codeSnippet"&gt;&lt;/span&gt;&lt;br /&gt;To specify which Encoding style to use, you need to use MemoryStream instead&lt;br /&gt;&lt;div id="XmlSerializerStreamOutput4" class="code"&gt;&lt;br /&gt;1.  XmlSerializer xs = new XmlSerializer(typeof(Foo));&lt;br /&gt;2.    using (MemoryStream ms = new MemoryStream())&lt;br /&gt;3.    {&lt;br /&gt;4.         XmlTextWriter xtwriter =new XmlTextWriter(ms, Encoding.UTF8);&lt;br /&gt;5.         xtwriter.Formatting = Formatting.None;&lt;br /&gt;6.         xs.Serialize(xtwriter, aFoo);&lt;br /&gt;7.         xtwriter.Flush();&lt;br /&gt;8.         ms.Position = 0;&lt;br /&gt;9.         XmlDocument doc = new XmlDocument();&lt;br /&gt;10.        doc.Load(new MemoryStream(ms.GetBuffer()) );&lt;br /&gt;11.   }&lt;br /&gt;&lt;/div&gt;&lt;br /&gt;And simplified version without encoding or style:&lt;br /&gt;&lt;div id="XmlSerializerStreamOutput4_1" class="code"&gt;&lt;br /&gt;1.  XmlSerializer xs = new XmlSerializer(typeof(Foo));&lt;br /&gt;2.  using (MemoryStream ms = new MemoryStream())&lt;br /&gt;3.  {&lt;br /&gt;4.   xs.Serialize(ms, item.Reviews);&lt;br /&gt;5.   XmlDocument doc = new XmlDocument();&lt;br /&gt;6.   doc.Load(new MemoryStream(ms.GetBuffer()) );&lt;br /&gt;7.   Console.WriteLine(doc.OuterXml);&lt;br /&gt;8.  }&lt;br /&gt;&lt;/div&gt;&lt;br /&gt;And finally, just be lazy - use Console.Out gives you a quick peek on what is produced:&lt;br /&gt;&lt;div id="XmlSerializerStreamOutput5" class="code"&gt;&lt;br /&gt;1.  XmlSerializer xs = new XmlSerializer(typeof(Foo));&lt;br /&gt;2.  xs.Serialize(Console.Out, aFoo);&lt;br /&gt;&lt;/div&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-112739313921626947?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/112739313921626947/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=112739313921626947' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/112739313921626947'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/112739313921626947'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2005/09/loading-xml-serialization-object-graph.html' title='Loading Xml Serialization Object Graph'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-112609544288440974</id><published>2005-09-16T17:43:00.000+01:00</published><updated>2006-11-01T12:31:45.001Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='sql'/><category scheme='http://www.blogger.com/atom/ns#' term='nant'/><category scheme='http://www.blogger.com/atom/ns#' term='Continuous Integration'/><title type='text'>Automated SQL Server database objects scripting and deployment in continuous integration environment</title><content type='html'>&lt;a href="http://photos1.blogger.com/blogger/4798/282/1600/Synchronisation.gif"&gt;&lt;img style="margin: 0pt 0pt 10px 10px; float: right; cursor: pointer;" src="http://photos1.blogger.com/blogger/4798/282/320/Synchronisation.gif" alt="" border="0" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;strong&gt;The initiatives&lt;/strong&gt;&lt;br /&gt;&lt;br /&gt;In the normal development lifecycle, database objects (tables, views,  stored procedures  and etc) evolve as implementation progressed. The despaired changes in each developer’s environment need to aggregate into the central CI build server then cascade to each developer’s environment. Normally this is done manually as there is at lack of source control mechanism for database objects.&lt;br /&gt;What we would like to have is an automated db objects scripting and release processes that we can plug into CC.Net or NAnt build process.&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;The Requirements:&lt;/strong&gt;&lt;br /&gt;&lt;em&gt;Iteration one:&lt;/em&gt;&lt;br /&gt;1) Automated (SQL Server) database scripting (DBGen.sql)&lt;br /&gt;2) Version control DBGen.sql. – Only update source/roll out changes when new changes are made.&lt;br /&gt;3) Assuming only one development machine is making changes to DB – so there is no need to consider builder server to development machines synchronisation.&lt;br /&gt;&lt;br /&gt;&lt;em&gt;Iteration two: Synchronisation&lt;/em&gt;Synchronous build server with development machines in a controlled way, i.e. only when a local development tasks has completed (build and tested) and the developer do a ‘Get Latest’ to sync the source code. The contrary to this is whenever changes to build server db is made and tests has been successful, using SQL backup/ replication/publish/subscription (?) mechanism to roll out the changes immediately.&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;Story break down (iteration one)&lt;/strong&gt;&lt;br /&gt;1. Post Build Event.&lt;br /&gt;DevEnv (Vs.net) uses post build event to trigger user database schema objects (tables, views, store procedures etc) scripting.&lt;br /&gt;  1) Post-build event command line that kicks off the db object scripting. This can be done in two ways:&lt;br /&gt;a. Scpriting (WScript/CScript) with ActiveX object SQLDMO. This option is more fine grain control on what objects to script.&lt;br /&gt;b. Command line executable using SQL Server upgrade facility. Scripts entire database in one go. (&lt;a href="http://www.dbazine.com/sql/sql-articles/larsen4"&gt;Scripting Database Objects&lt;/a&gt; has detail introduction.)&lt;br /&gt;  2) Check file size (not sum size) on the generated DBGen.sql, auto check out the source control version if there are difference, - but do not check it in yet.&lt;br /&gt;&lt;br /&gt;(Developer checks in all changes)&lt;br /&gt;2. Release decision.&lt;br /&gt;Decide whether there is a need to release new db schema by checking the source safe version and time stamp. This process needs to be built into Nant build process.&lt;br /&gt;&lt;br /&gt;3. Run DBGen.sql&lt;br /&gt;(If release required) DBGen.sql is executed by Nant using WMI and blah blah blah…&lt;br /&gt;DBGen.sql is run after successful build, before unit tests.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-112609544288440974?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/112609544288440974/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=112609544288440974' title='2 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/112609544288440974'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/112609544288440974'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2005/09/automated-sql-server-database-objects.html' title='Automated SQL Server database objects scripting and deployment in continuous integration environment'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><thr:total>2</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-112682671842362981</id><published>2005-09-16T00:25:00.000+01:00</published><updated>2006-11-01T12:05:01.135Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='sql'/><category scheme='http://www.blogger.com/atom/ns#' term='nant'/><title type='text'>Scripting Database Objects</title><content type='html'>&lt;a href="http://www.dbazine.com/sql/sql-articles/larsen4"&gt;DBAzine.com: Scripting Database Objects&lt;/a&gt; have some very good advice on command line Sql Server database objects (tables, index, store procedures etc) scripting. This is extremely useful on automated build process using NAnt. Basically you can run this command to generate db objects except database itself.&lt;br /&gt;The script is created by executed this command:&lt;br /&gt;&lt;div id="sqldbscript" class="code"&gt;&lt;br /&gt;C:\Program Files\Microsoft SQL Server\MSSQL\Upgrade&gt;scptxfr.exe /s &lt;sqlservername&gt; /d &lt;dbname&gt; /I /f DBExtract.sql /q /r /H /Y&lt;br /&gt;&lt;/dbname&gt;&lt;/sqlservername&gt;&lt;/div&gt;&lt;br /&gt;Then concatenate it with the 'standard' database drop and creation script produced with Enterprise Manager - All Tasks - Generate SQL Script (with only script database option)&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-112682671842362981?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='related' href='http://www.dbazine.com/sql/sql-articles/larsen4' title='Scripting Database Objects'/><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/112682671842362981/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=112682671842362981' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/112682671842362981'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/112682671842362981'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2005/09/scripting-database-objects.html' title='Scripting Database Objects'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-112633900779031089</id><published>2005-09-10T08:56:00.000+01:00</published><updated>2006-11-01T12:06:24.805Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='win server'/><title type='text'>WMI useful sites for beginner</title><content type='html'>&lt;a href="http://www.microsoft.com/technet/scriptcenter/guide/default.mspx"&gt;Microsoft - Introduction to Windows Script Technologies&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;&lt;a href="http://www.computerperformance.co.uk/vbscript/wmi.htm"&gt;WMI and VBScript for Microsoft Operating Systems&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;&lt;a href="http://www.databasejournal.com/features/mssql/article.php/1503181"&gt;Automating SQL Server Management with WMI (Part 1)&lt;/a&gt;&lt;br /&gt;(there are 5 parts in total)&lt;br /&gt;&lt;br /&gt;&lt;a href="http://www.sqlservercentral.com/columnists/aloera/sqlserverscriptingandwmi.asp"&gt;SQL Server Scripting and WMI&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;This should get me busy this Saturday.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-112633900779031089?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='related' href='http://www.computerperformance.co.uk/vbscript/wmi.htm' title='WMI useful sites for beginner'/><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/112633900779031089/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=112633900779031089' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/112633900779031089'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/112633900779031089'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2005/09/wmi-useful-sites-for-beginner.html' title='WMI useful sites for beginner'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-112627457389313161</id><published>2005-09-09T15:02:00.000+01:00</published><updated>2006-11-01T12:07:03.871Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='xml'/><title type='text'>XML extensibility, xsi:type, XmlSerializer and configuration (or how to leverage XmlSerializer + OO extensibility)</title><content type='html'>Daniel Cazzulino got this smashing discussion on &lt;a href="http://weblogs.asp.net/cazzu/archive/2004/01/23/62141.aspx"&gt;XML extensibility, xsi:type, XmlSerializer and configuration (or how to leverage XmlSerializer + OO extensibility)&lt;/a&gt;: "XmlSerializer ser = new XmlSerializer( typeof( People ), new Type[] { typeof( Employee ) } );"&lt;br /&gt;&lt;br /&gt;To sum up, this is a pattern on leverage OO inheritance and XML extensibility.&lt;br /&gt;&lt;br /&gt;We want to produce a schema like this (sample data)&lt;br /&gt;&lt;div id="samplexmldata1" class="code"&gt;&lt;br /&gt;&amp;lt;?xml version="1.0" encoding="utf-16" ?&amp;gt;&lt;br /&gt;&amp;lt;Products xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"&lt;br /&gt; xmlns="http://whatever.com/example/DataTypes.xsd"&amp;gt;&lt;br /&gt; &amp;lt;Vehicle xsi:type="Car" Price="20000" Fuel="Petrol" Chassis="Saloon"&amp;gt;&lt;br /&gt;  &amp;lt;VIN&amp;gt;070121SD1T69079YFW&amp;lt;/VIN&amp;gt;&lt;br /&gt;  &amp;lt;Brand&amp;gt;AUDI&amp;lt;/Brand&amp;gt;&lt;br /&gt;  &amp;lt;Comfort&amp;gt;Climate Control, CD&amp;lt;/Comfort&amp;gt;&lt;br /&gt;  &amp;lt;Safe&amp;gt;ABS, Twin Airbage&amp;lt;/safe&amp;gt;&lt;br /&gt; &amp;lt;/Vehicle&amp;gt;&lt;br /&gt; &amp;lt;Vehicle xsi:type="Tractor" Price="22000" Fuel="Diesel"&amp;gt;&lt;br /&gt;  &amp;lt;VIN&amp;gt;01211334SD9079YFW&amp;lt;/VIN&amp;gt;&lt;br /&gt;  &amp;lt;Brand&amp;gt;Famer's Friend&amp;lt;/Brand&amp;gt;&lt;br /&gt;  &amp;lt;FieldTools&amp;gt;Wrench&amp;lt;/FieldTools&amp;gt;&lt;br /&gt; &amp;lt;/Vehicle&amp;gt;&lt;br /&gt;&amp;lt;/Products&amp;gt;&lt;br /&gt;&lt;/div&gt;&lt;br /&gt;the scehma:&lt;br /&gt;&lt;br /&gt;&lt;div id="sampleschema" class="code"&gt;&lt;br /&gt;namespace ClassLibrary1&lt;br /&gt;{&lt;br /&gt; using System.Xml;&lt;br /&gt; using System.Xml.Serialization;&lt;br /&gt;&lt;br /&gt; [System.Xml.Serialization.XmlTypeAttribute(Namespace="http://whatever.com/example/DataTypes.xsd")]&lt;br /&gt; [XmlRootAttribute(Namespace="http://whatever.com/example/DataTypes.xsd", IsNullable=false)]&lt;br /&gt; public class Products&lt;br /&gt; {&lt;br /&gt;  [XmlElement("Vehicle", typeof(Vehicle))]&lt;br /&gt;  public Vehicle[] Item;&lt;br /&gt; }&lt;br /&gt;&lt;br /&gt; [System.Xml.Serialization.XmlTypeAttribute(Namespace="http://whatever.com/example/DataTypes.xsd")]&lt;br /&gt; public class Vehicle&lt;br /&gt; {&lt;br /&gt;  /// &amp;lt;summary&amp;gt;retail price&amp;lt;/summary&amp;gt;&lt;br /&gt;  [XmlAttributeAttribute("Price")]&lt;br /&gt;  public virtual double Price&lt;br /&gt;  {&lt;br /&gt;   get { return _price; }&lt;br /&gt;   set { _price = value; }&lt;br /&gt;  }double _price;&lt;br /&gt;&lt;br /&gt;  /// &amp;lt;summary&amp;gt;Fuel Type&amp;lt;/summary&amp;gt;  &lt;br /&gt;  [XmlAttributeAttribute("Fuel")]&lt;br /&gt;  public virtual string Fuel&lt;br /&gt;  {&lt;br /&gt;   get { return _fuel; }&lt;br /&gt;   set { _fuel = value; }&lt;br /&gt;  }string _fuel;&lt;br /&gt;&lt;br /&gt;  /// &amp;lt;summary&amp;gt;Vihicle Identifer Number&amp;lt;/summary&amp;gt;&lt;br /&gt;  [XmlElementAttribute("Vin")]&lt;br /&gt;  public virtual string Vin&lt;br /&gt;  {&lt;br /&gt;   get { return _vin;}&lt;br /&gt;   set { _vin = value;}&lt;br /&gt;  }string _vin;&lt;br /&gt;&lt;br /&gt;  /// &amp;lt;summary&amp;gt;Vihicle brand name&amp;lt;/summary&amp;gt;&lt;br /&gt;  [XmlElementAttribute("Brand")]&lt;br /&gt;  public virtual string Brand&lt;br /&gt;  {&lt;br /&gt;   get { return _brand;}&lt;br /&gt;   set { _brand = value;}&lt;br /&gt;  }string _brand;&lt;br /&gt;&lt;br /&gt;  // make the Record xml schema extensible&lt;br /&gt;  [XmlAnyElement()]&lt;br /&gt;  public XmlElement[] AllElements;&lt;br /&gt;&lt;br /&gt;  [XmlAnyAttribute()]&lt;br /&gt;  public XmlAttribute[] AllAttributes;&lt;br /&gt; }&lt;br /&gt;&lt;br /&gt; [XmlTypeAttribute(Namespace="http://whatever.com/example/DataTypes.xsd" )]&lt;br /&gt; [XmlRoot("Vehicle")]&lt;br /&gt; public class Car : Vehicle&lt;br /&gt; {&lt;br /&gt;  [XmlAttributeAttribute("Chassis")]&lt;br /&gt;  public string Chassis;&lt;br /&gt;  /// &amp;lt;summary&amp;gt;Vihicle brand name&amp;lt;/summary&amp;gt;&lt;br /&gt;&lt;br /&gt;  [XmlElementAttribute("Comfort")]&lt;br /&gt;  public virtual string ComfortPack&lt;br /&gt;  {&lt;br /&gt;   get { return _comfortPack;}&lt;br /&gt;   set { _comfortPack = value;}&lt;br /&gt;  }string _comfortPack;&lt;br /&gt;&lt;br /&gt;  /// &amp;lt;summary&amp;gt;Vihicle brand name&amp;lt;/summary&amp;gt;&lt;br /&gt;&lt;br /&gt;  [XmlElementAttribute("Safe")]&lt;br /&gt;  public virtual string SaftyDevice&lt;br /&gt;  {&lt;br /&gt;   get { return _saftyDevice; }&lt;br /&gt;   set { _saftyDevice = value; }&lt;br /&gt;  }string _saftyDevice;&lt;br /&gt; }&lt;br /&gt;&lt;br /&gt; public class Tractor : Vehicle&lt;br /&gt; {&lt;br /&gt;  /// &amp;lt;summary&amp;gt;field tools included&amp;lt;/summary&amp;gt;&lt;br /&gt;  [XmlElement("FieldTools")]&lt;br /&gt;  public virtual string FieldTools&lt;br /&gt;  {&lt;br /&gt;   get { return _fieldTools; }&lt;br /&gt;   set { _fieldTools = value; }&lt;br /&gt;  }string _fieldTools;&lt;br /&gt; }&lt;br /&gt;}&lt;br /&gt;&lt;/div&gt;&lt;br /&gt;Now to serialize the following object, I created a Nunit Test case to run it, very handy.&lt;br /&gt;&lt;br /&gt;&lt;div id="testcode" class="code"&gt;&lt;br /&gt;using System;&lt;br /&gt;using NUnit.Framework;&lt;br /&gt;&lt;br /&gt;namespace ClassLibrary1 {&lt;br /&gt; using System.IO;&lt;br /&gt; using System.Xml;&lt;br /&gt; using System.Xml.Serialization;&lt;br /&gt;&lt;br /&gt; [TestFixture]&lt;br /&gt; public class TestClass1 {&lt;br /&gt;&lt;br /&gt;  [SetUp]&lt;br /&gt;  public void SetUp() {}&lt;br /&gt;&lt;br /&gt;  [TearDown]&lt;br /&gt;  public void TearDown() {}&lt;br /&gt;&lt;br /&gt;  [Test] public void Test()&lt;br /&gt;  {&lt;br /&gt;   Car car1 = new Car();&lt;br /&gt;   car1.Chassis = "Saloon";&lt;br /&gt;   car1.ComfortPack = "Climate Control, CD";&lt;br /&gt;   car1.SaftyDevice = "ABS, Twin Airbage";&lt;br /&gt;   car1.Brand = "AUDI";&lt;br /&gt;   car1.Fuel = "Petrol";&lt;br /&gt;   car1.Price = 20000.00;&lt;br /&gt;   car1.Vin = "070121SD1T69079YFW";&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;   Tractor tractor1 = new Tractor();&lt;br /&gt;   tractor1.Brand = "Famer's Friend";&lt;br /&gt;   tractor1.FieldTools = "Wrench";&lt;br /&gt;   tractor1.Fuel = "Diesel";&lt;br /&gt;   tractor1.Price = 22000;&lt;br /&gt;   tractor1.Vin = "01211334SD9079YFW";&lt;br /&gt;&lt;br /&gt;   Products p = new Products();&lt;br /&gt;   p.Item = new Vehicle[] {car1, tractor1} ;&lt;br /&gt;&lt;br /&gt;   //The most critical step, add the extended type to schema, so serializer knows what to to do&lt;br /&gt;   XmlSerializer serializer = new XmlSerializer( typeof( Products ), new Type[] {typeof(Car), typeof(Tractor)} );&lt;br /&gt;   StringWriter writer = new StringWriter();&lt;br /&gt;&lt;br /&gt;   serializer.Serialize(writer, p);&lt;br /&gt;   XmlDocument actual = new XmlDocument();   &lt;br /&gt;   actual.LoadXml(writer.ToString());&lt;br /&gt;   Console.WriteLine(actual.OuterXml);&lt;br /&gt;  }&lt;br /&gt; }&lt;br /&gt;}&lt;br /&gt;&lt;/div&gt;&lt;br /&gt;This should produce the sample data as shown above.&lt;br /&gt;&lt;br /&gt;Question: what are AllElements, AllAttributes in Vichicle class for?&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-112627457389313161?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='related' href='http://weblogs.asp.net/cazzu/archive/2004/01/23/62141.aspx' title='XML extensibility, xsi:type, XmlSerializer and configuration (or how to leverage XmlSerializer + OO extensibility)'/><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/112627457389313161/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=112627457389313161' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/112627457389313161'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/112627457389313161'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2005/09/xml-extensibility-xsitype.html' title='XML extensibility, xsi:type, XmlSerializer and configuration (or how to leverage XmlSerializer + OO extensibility)'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-112618385436593097</id><published>2005-09-08T13:50:00.000+01:00</published><updated>2006-11-01T12:07:48.442Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='xml'/><title type='text'>XML Schema best practice guideline</title><content type='html'>&lt;a href="http://xml.coverpages.org/HP-StephensonSchemaBestPractices.pdf"&gt;&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;Found this XML Schema best practice guideline by David Stephenson.&lt;br /&gt;Here is the summary.&lt;br /&gt;1. General Meta requirements for XML schemas:&lt;br /&gt;Understandable&lt;br /&gt;Semantically complete&lt;br /&gt;Constraining (i.e. validate)&lt;br /&gt;Non-redundant&lt;br /&gt;Reusable&lt;br /&gt;Extensible&lt;br /&gt;Non-modifying&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;Attributes vs. elements&lt;/strong&gt;&lt;br /&gt;There is no real consensus on when to use attributes or elements. Here are best practices to help you choose when writing your XML schema.&lt;br /&gt;a. Use attributes for metadata about the parent element (foo is the parent element in the example above).&lt;br /&gt;&lt;br /&gt;b. Use attributes for data that is semantically tied to the enclosing element.&lt;br /&gt;&lt;br /&gt;c. Use elements for data that have a meaning separate from the enclosing element.&lt;br /&gt;&lt;br /&gt;d. Use attributes when the value will be frequently present in order to improve the human readable form of an XML instance document or reduce its size.&lt;br /&gt;&lt;br /&gt;e. If you don't know which to use, then use the element form (which is more extensible).&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;Always define elements globally. Elements within model groups (choice, sequence) should always use the ref= form and never the type= form.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-112618385436593097?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='related' href='http://xml.coverpages.org/HP-StephensonSchemaBestPractices.pdf' title='XML Schema best practice guideline'/><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/112618385436593097/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=112618385436593097' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/112618385436593097'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/112618385436593097'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2005/09/found-this-xml-schema-best-practice.html' title='XML Schema best practice guideline'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-112602052011016176</id><published>2005-09-06T16:20:00.000+01:00</published><updated>2006-11-01T12:08:29.835Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='.net'/><title type='text'>Putting binary object into .net resource file</title><content type='html'>&lt;a href="http://photos1.blogger.com/blogger/4798/282/1600/ResourceData1.jpg"&gt;&lt;img style="margin: 0pt 0pt 10px 10px; float: right; cursor: pointer;" src="http://photos1.blogger.com/blogger/4798/282/320/ResourceData1.jpg" alt="" border="0" /&gt;&lt;/a&gt;&lt;br /&gt;Before I delete (and forget) how to import binary object such like image into .Net resouce file here is the script to do it with Nunit.&lt;br /&gt;&lt;br /&gt;&lt;div id="pboirf" class="code"&gt;&lt;br /&gt; [Test]&lt;br /&gt; [Ignore("Use this test to create resource file only")]&lt;br /&gt; public void WriteResouceFile()&lt;br /&gt; {&lt;br /&gt;  ResXResourceWriter  rsxw = new ResXResourceWriter("TestData.resx");&lt;br /&gt;  rsxw.AddResource("BirdsBritannica_JacketImage",Image.FromFile("BirdsBritannica.jpg"));&lt;br /&gt;  rsxw.AddResource("BirdsBritannica_Title","Birds Britannica");&lt;br /&gt;  rsxw.AddResource("BirdsBritannica_Review","Another magnificent achievement and a unique work ... ");&lt;br /&gt;  rsxw.AddResource("BirdsBritannica_ISBN","0701169079");&lt;br /&gt; &lt;br /&gt;  rsxw.AddResource("Coast_JacketImage",Image.FromFile("Coast.jpg"));&lt;br /&gt;  rsxw.AddResource("Coast_Title","Coast");&lt;br /&gt;  rsxw.AddResource("Coast_Review","Accompanying the BBC series, Coast is not only a superbly illustrated ...");&lt;br /&gt;  rsxw.AddResource("Coast_ISBN","0563522798");&lt;br /&gt;&lt;br /&gt;  rsxw.AddResource("TheDaVinciCode_JacketImage",Image.FromFile("TheDaVinciCode.jpg"));&lt;br /&gt;  rsxw.AddResource("TheDaVinciCode_Title","The Da Vinci Code");&lt;br /&gt;  rsxw.AddResource("TheDaVinciCode_Review",@"With The Da Vinci Code, Dan Brown masterfully concocts an intelligent...");&lt;br /&gt;  rsxw.AddResource("TheDaVinciCode_ISBN","0552149519");&lt;br /&gt;  rsxw.Close();&lt;br /&gt; }&lt;br /&gt;&lt;/div&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-112602052011016176?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/112602052011016176/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=112602052011016176' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/112602052011016176'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/112602052011016176'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2005/09/putting-binary-object-into-net.html' title='Putting binary object into .net resource file'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-112556653633189500</id><published>2005-09-01T10:22:00.000+01:00</published><updated>2006-11-01T12:09:47.003Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='win server'/><title type='text'>Windows Keyboard Shortcuts</title><content type='html'>Not really have much fun with the touch pad (or 'nipple') of the laptop I am using.&lt;br /&gt;The best hotkey stokes of all are:&lt;br /&gt;Run Dialog              WIN + R&lt;br /&gt;Minimize All             WIN + M&lt;br /&gt;Undo Minimize All     SHIFT - WIN + M&lt;br /&gt;Explorer                 WIN + E&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-112556653633189500?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='related' href='http://www.eastserve.com/opencms/opencms/My_Computer/help_support/keyboard.html' title='Windows Keyboard Shortcuts'/><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/112556653633189500/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=112556653633189500' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/112556653633189500'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/112556653633189500'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2005/09/windows-keyboard-shortcuts.html' title='Windows Keyboard Shortcuts'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-112518100587601461</id><published>2005-08-27T22:57:00.000+01:00</published><updated>2006-11-01T12:10:30.937Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='not work'/><title type='text'>a recent visit to Paris and Rome</title><content type='html'>&lt;a href="http://photos1.blogger.com/blogger/4798/282/1600/Austria1180_1076.jpg"&gt;&lt;img style="margin: 0pt 10px 10px 0pt; float: left; cursor: pointer;" src="http://photos1.blogger.com/blogger/4798/282/320/Austria1180_1076.jpg" alt="" border="0" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;&lt;a href="http://photos1.blogger.com/blogger/4798/282/1600/Rome1.jpg"&gt;&lt;img style="margin: 0px 10px 10px 0px; float: left;" alt="" src="http://photos1.blogger.com/blogger/4798/282/320/Rome1.jpg" border="0" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;&lt;a href="http://photos1.blogger.com/blogger/4798/282/1600/france1280_1024.jpg"&gt;&lt;img style="margin: 0px 10px 10px 0px; float: left;" alt="" src="http://photos1.blogger.com/blogger/4798/282/320/france1280_1024.jpg" border="0" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;Feel free to click and see the full size of it. Hope it wouldn't make you go colour blind :-)&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-112518100587601461?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/112518100587601461/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=112518100587601461' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/112518100587601461'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/112518100587601461'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2005/08/recent-visit-to-paris-and-rome.html' title='a recent visit to Paris and Rome'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-112236905137664890</id><published>2005-07-26T10:08:00.000+01:00</published><updated>2006-11-01T12:11:07.148Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='html css'/><title type='text'>CSS Styling Borders</title><content type='html'>&lt;a href="http://photos1.blogger.com/blogger/4798/282/1600/css1.gif"&gt;&lt;img style="margin: 0pt 0pt 10px 10px; float: right; cursor: pointer;" src="http://photos1.blogger.com/blogger/4798/282/200/css1.gif" alt="" border="0" /&gt;&lt;/a&gt;&lt;br /&gt;Got this from the book &lt;a href="http://www.amazon.co.uk/exec/obidos/ASIN/073571245X/httifotnet-21"&gt;Eric Meyer on CSS&lt;/a&gt;. Very light and hands-on work book. I found this CSS section that creates left hand navigation bar border is very interesting. Sometime seemed a haunting job to me.&lt;br /&gt;The first version with HTML:&lt;br /&gt;&lt;div id="html1" class="code"&gt;&lt;br /&gt;&amp;lt;html&amp;gt;&lt;br /&gt;       &amp;lt;head&amp;gt;&lt;br /&gt;               &amp;lt;meta http-equiv="Content-Type" content="text/html; charset=utf-8"&amp;gt;&lt;br /&gt;               &amp;lt;title&amp;gt;Chapter 5 Project&amp;lt;/title&amp;gt;&lt;br /&gt;               &amp;lt;style type="text/css"&amp;gt;&lt;br /&gt;                       body {background-color: rgb(100%,98%,96%); color: black;}&lt;br /&gt;                       td {border-width: 0; padding: 0;}&lt;br /&gt;                       td#banner {border-bottom: 2px solid rgb(60%,50%,40%);}&lt;br /&gt;                       td#banner h1 {color: rgb(40%,30%,20%);&lt;br /&gt;                               margin: 0; padding: 0.25em 0 0.125em 0;&lt;br /&gt;                               font: bold 150% sans-serif; letter-spacing: 0.5em;}&lt;br /&gt;                       td#main {background-color: transparent; color: black;&lt;br /&gt;                               padding: 1em; font: 95% Times, serif;}&lt;br /&gt;                       td#main h2 {font: bold 125% sans-serif;&lt;br /&gt;                               margin: 0.5em 1em; padding: 0;&lt;br /&gt;                               border-bottom: 1px solid rgb(80%,75%,70%);}&lt;br /&gt;                       td#main p {margin: 1em 2.5em;}&lt;br /&gt;                      &lt;br /&gt;                       /* menu style: the hovering link block has right border overlay the menu border line*/&lt;br /&gt;                       td#sidelinks {vertical-align: top;}&lt;br /&gt;                       td#sidelinks a, td#sidelinks h4 {margin:0 3px 0 0; font: bold 100% Arial, Verdana, sans-serif;border-right: 1px solid rgb(60%, 50%, 40%); background: transparent;}&lt;br /&gt;                       td#sidelinks a {display:block; text-decoration: none; padding: 1px 10px 1px 5px; color: rgb(30%, 30%, 60%);}&lt;br /&gt;                       td#sidelinks a:visited {color: rgb(55%, 55%, 60%);}&lt;br /&gt;                       td#sidelinks a:hover, td#sidelinks a:focus{ background-color: rgb(100%, 70%, 70%); color: rgb(50%, 0%, 0%); border-right: 7px solid rgb(80% 30% 20%); padding-right: 7px; margin-right: 0px;}&lt;br /&gt;                       td#sidelinks h4 {background-color: transparent; color: rgb(30%, 20%. 10%; margin: 0 3px 0 0; padding 1em 0 0; font: bold 100% Arial, Verdana, sans-serif; border-bottom: 2px solid rgb(50%, 40%, 30%); border-right: 1px solid rgb(60%, 50%, 40%); }&lt;br /&gt;                       td#sidelinks a#comment{ background-color: rgb(100%, 92% 90%); color: black; border: 1px solid rgb(60%, 50%, 40%);  border-right-width: 4px; padding-right:7px; margin-right: 3px;}&lt;br /&gt;&lt;br /&gt;                       td#footer {background-color: transparent; color: rgb(70%,60%,50%);&lt;br /&gt;                               border-top: 1px solid rgb(60%,50%,40%);&lt;br /&gt;                               text-align: right; font-size: 85%;&lt;br /&gt;                               padding-top: 0.33em; font-style: italic;}&lt;br /&gt;               &amp;lt;/style&amp;gt;&lt;br /&gt;       &amp;lt;/head&amp;gt;&lt;br /&gt;       &amp;lt;body&amp;gt;&lt;br /&gt;               &amp;lt;table cellspacing="0"&amp;gt;&lt;br /&gt;                       &amp;lt;tr&amp;gt;&lt;br /&gt;                               &amp;lt;td colspan="2" id="banner"&amp;gt;&amp;lt;h1&amp;gt;Styling With EM&amp;lt;/h1&amp;gt;&lt;br /&gt;                               &amp;lt;/td&amp;gt;&lt;br /&gt;                       &amp;lt;/tr&amp;gt;&lt;br /&gt;                       &amp;lt;tr&amp;gt;&lt;br /&gt;                               &amp;lt;td id="sidelinks"&amp;gt;&lt;br /&gt;                                       &amp;lt;h4&amp;gt;Standards&amp;lt;/h4&amp;gt;&lt;br /&gt;                                       &amp;lt;a href="html.html" id="html"&amp;gt;HTML&amp;lt;/a&amp;gt; &amp;lt;a href="xhtml.html" id="xhtml"&amp;gt;XHTML&amp;lt;/a&amp;gt;&lt;br /&gt;&lt;br /&gt;                                       &amp;lt;a href="css.html" id="css"&amp;gt;CSS&amp;lt;/a&amp;gt; &amp;lt;a href="dom.html" id="dom"&amp;gt;DOM&amp;lt;/a&amp;gt;&lt;br /&gt;                                       &amp;lt;h4&amp;gt;Extras&amp;lt;/h4&amp;gt;&lt;br /&gt;                                       &amp;lt;a href="tools.html" id="tools"&amp;gt;Tools&amp;lt;/a&amp;gt; &amp;lt;a href="review.html" id="reviews"&amp;gt;Reviews&amp;lt;/a&amp;gt;&lt;br /&gt;&lt;br /&gt;                                       &amp;lt;a href="comment.html" id="comment"&amp;gt;Commentary&amp;lt;/a&amp;gt; &amp;lt;a href="weblog.html" id="weblog"&amp;gt;&lt;br /&gt;                                               Weblog&amp;lt;/a&amp;gt;&lt;br /&gt;                                       &amp;lt;h4&amp;gt;Basic&amp;lt;/h4&amp;gt;&lt;br /&gt;                                       &amp;lt;a href="contact.html" id="contact"&amp;gt;Contact&amp;lt;/a&amp;gt; &amp;lt;a href="index.html" id="home"&amp;gt;Home&amp;lt;/a&amp;gt;&lt;br /&gt;&lt;br /&gt;                               &amp;lt;/td&amp;gt;&lt;br /&gt;                               &amp;lt;td id="main"&amp;gt;&lt;br /&gt;                                       &amp;lt;h2&amp;gt;On Being a Web Mechanic&amp;lt;/h2&amp;gt;&lt;br /&gt;                                       &amp;lt;p&amp;gt;Once upon a time-- okay,…&amp;lt;/p&amp;gt;&lt;br /&gt;                                       &amp;lt;p&amp;gt;Once upon a time-- okay,…&amp;lt;/p&amp;gt;&lt;br /&gt;                                       &amp;lt;p&amp;gt;Once upon a time-- okay,…&amp;lt;/p&amp;gt;&lt;br /&gt;                               &amp;lt;/td&amp;gt;&lt;br /&gt;                       &amp;lt;/tr&amp;gt;&lt;br /&gt;                       &amp;lt;tr&amp;gt;&lt;br /&gt;                               &amp;lt;td colspan="2" id="footer"&amp;gt;Copyright 2001 Eric A. Meyer. All Rights Reserved.&amp;lt;/td&amp;gt;&lt;br /&gt;                       &amp;lt;/tr&amp;gt;&lt;br /&gt;               &amp;lt;/table&amp;gt;&lt;br /&gt;       &amp;lt;/body&amp;gt;&lt;br /&gt;&amp;lt;/html&amp;gt;&lt;br /&gt;&lt;/div&gt;&lt;br /&gt;Some variations - double line border:&lt;br /&gt;&lt;div id="html2" class="code"&gt;&lt;br /&gt;  /* menu style: the hovering link block has right border overlay the menu border line*/&lt;br /&gt;  td#sidelinks {vertical-align: top;}&lt;br /&gt;  td#sidelinks a, td#sidelinks h4 {margin:0 3px 0 0; font: bold 100% Arial, Verdana, sans-serif;&lt;br /&gt;                       /* border-right: 1px solid rgb(60%, 50%, 40%); */border-right: rgb(60%, 50%, 40%) 4px double; background: transparent;}&lt;br /&gt;  td#sidelinks a {display:block;  text-decoration: none; padding: 1px 10px 1px 5px; color: rgb(30%, 30%, 60%);}&lt;br /&gt;  td#sidelinks a:visited {color: rgb(55%, 55%, 60%);}&lt;br /&gt;  td#sidelinks a:hover, td#sidelinks a:focus{ background-color: rgb(100%, 70%, 70%);color: rgb(50%, 0%, 0%);border-right: 4px solid rgb(80% 30% 20%);padding-right: 7px;margin-right: 3px;}              &lt;br /&gt;  td#sidelinks h4 {background-color: transparent; color: rgb(30%, 20%, 10%;&lt;br /&gt;           margin: 0 3px 0 0; padding 1em 0 0;&lt;br /&gt;           font: bold 100% Arial, Verdana, sans-serif;&lt;br /&gt;           border-bottom: 2px solid rgb(50%, 40%, 30%);&lt;br /&gt;           /* border-right: 1px solid rgb(60%, 50%, 40%); */&lt;br /&gt;           border-right: rgb(60%, 50%, 40%) 4px double;&lt;br /&gt;           }&lt;br /&gt;  td#sidelinks a#comment{ background-color: rgb(100%, 92% 90%); color: black;border: 1px solid rgb(60%, 50%, 40%); border-right-width: 4px; padding-right:7px; margin-right: 3px;}&lt;br /&gt;&lt;/div&gt;&lt;br /&gt;icon image border&lt;br /&gt;&lt;div id="html3" class="code"&gt;&lt;br /&gt;  /* menu style: the hovering link block has right border overlay the menu border line*/&lt;br /&gt;  td#sidelinks {vertical-align: top;}&lt;br /&gt;  td#sidelinks a, td#sidelinks h4 {margin:0 3px 0 0; font: bold 100% Arial, Verdana, sans-serif;&lt;br /&gt;                       /* border-right: 1px solid rgb(60%, 50%, 40%); */border-right: rgb(60%, 50%, 40%) 4px double; background: transparent;}&lt;br /&gt;  td#sidelinks a {display:block;  text-decoration: none; padding: 1px 10px 1px 5px; color: rgb(30%, 30%, 60%);}&lt;br /&gt;  td#sidelinks a:visited {color: rgb(55%, 55%, 60%);}&lt;br /&gt;  td#sidelinks a:hover, td#sidelinks a:focus{ background-color: rgb(100%, 70%, 70%);color: rgb(50%, 0%, 0%);border-right: 4px solid rgb(80% 30% 20%);padding-right: 7px;margin-right: 3px;}              &lt;br /&gt;  td#sidelinks h4 {background-color: transparent; color: rgb(30%, 20%, 10%;&lt;br /&gt;           margin: 0 3px 0 0; padding 1em 0 0;&lt;br /&gt;           font: bold 100% Arial, Verdana, sans-serif;&lt;br /&gt;           border-bottom: 2px solid rgb(50%, 40%, 30%);&lt;br /&gt;           /* border-right: 1px solid rgb(60%, 50%, 40%); */&lt;br /&gt;           border-right: rgb(60%, 50%, 40%) 4px double;&lt;br /&gt;           }&lt;br /&gt;  td#sidelinks a#comment{ background-color: rgb(100%, 92% 90%); color: black;border: 1px solid rgb(60%, 50%, 40%); border-right-width: 4px; padding-right:7px; margin-right: 3px;}&lt;br /&gt;&lt;br /&gt;&lt;br /&gt; /* menu style: the hovering link block has right border overlay the menu border line*/&lt;br /&gt;  td#sidelinks {vertical-align: top;}&lt;br /&gt;  td#sidelinks a, td#sidelinks h4 {margin:0 3px 0 0;font: bold 100% Arial, Verdana, sans-serif;border-right: 1px solid rgb(60%, 50%, 40%);background: transparent;}&lt;br /&gt;  td#sidelinks a {display:block;text-decoration: none; padding: 1px 10px 1px 5px; color: rgb(30%, 30%, 60%);}&lt;br /&gt;  td#sidelinks a:visited {color: rgb(55%, 55%, 60%);}&lt;br /&gt;  td#sidelinks a:hover, td#sidelinks a:focus{ background-color: rgb(100%, 70%, 70%);color: rgb(50%, 0%, 0%);border-right: 7px solid rgb(80% 30% 20%);background-image: url(arrow.gif); background-repeat: no-repeat;background-position: 94% 50%; padding-right: 7px;margin-right: 0px;}&lt;br /&gt;  td#sidelinks h4 {background-color: transparent; color: rgb(30%, 20%. 10%; margin: 0 3px 0 0; padding 1em 0 0; font: bold 100% Arial, Verdana, sans-serif;border-bottom: 2px solid rgb(50%, 40%, 30%); border-right: 1px solid rgb(60%, 50%, 40%);}&lt;br /&gt;  td#sidelinks a#comment{ background-color: rgb(100%, 92% 90%); color: black;background-image: url(arrow2.gif);ackground-repeat: no-repeat;background-position: 96% 50%;border: 1px solid rgb(60%, 50%, 40%); border-right-width: 4px; padding-right:7px; margin-right: 3px;}&lt;br /&gt;&lt;/div&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-112236905137664890?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/112236905137664890/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=112236905137664890' title='1 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/112236905137664890'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/112236905137664890'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2005/07/css-styling-borders.html' title='CSS Styling Borders'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><thr:total>1</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-112229876104294724</id><published>2005-07-25T14:18:00.000+01:00</published><updated>2006-11-01T12:11:41.069Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='not work'/><title type='text'>Up Sticks</title><content type='html'>I am leaving this famous online Bank in August to join a software house specialised in Learning and Library software. Has been with this Bank for around three years, I think it is good to take in some fresh air and move on.&lt;br /&gt;&lt;br /&gt;My new employer does Test Driven development, on .NET and Java platforms. There are loads of challenges in the eXtreme Programming software engineering, new technologies -.Net, XML parser, Web Services, Image search etc to play with. I think it is good to broaden my profile.&lt;br /&gt;&lt;br /&gt;Happen to read Steve Jobs’ &lt;a href="http://news-service.stanford.edu/news/2005/june15/jobs-061505.html"&gt;recent speech at Stanford&lt;/a&gt;, which couldn’t describe what I think better.&lt;br /&gt;&lt;br /&gt;&lt;em&gt;‘I'm pretty sure none of this would have happened if I hadn't been fired from Apple. It was awful tasting medicine, but I guess the patient needed it. Sometimes life hits you in the head with a brick. Don't lose faith. I'm convinced that the only thing that kept me going was that I loved what I did. You've got to find what you love. And that is as true for your work as it is for your lovers. Your work is going to fill a large part of your life, and the only way to be truly satisfied is to do what you believe is great work. And the only way to do great work is to love what you do.’&lt;/em&gt;&lt;br /&gt;&lt;br /&gt;I will be then driving 36 miles south down notorious M6 J10-J4 section instead of going east 35 miles down the picturesque A518 and A50. I probably will give up driving altogether with pushbike and commuter train, which saves around 2 hours a day.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-112229876104294724?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/112229876104294724/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=112229876104294724' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/112229876104294724'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/112229876104294724'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2005/07/up-sticks.html' title='Up Sticks'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-112172461633014191</id><published>2005-07-18T23:10:00.000+01:00</published><updated>2006-11-01T12:12:31.225Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='idea'/><title type='text'>Delicious Library and more</title><content type='html'>Traditional media are tangible: books, CD, VHS tape. We consume them, collect them, shelf them in our personal libraries. Over years the collection grows and we are satisfied because we ‘own’ something that you can touch and feel it.&lt;br /&gt;&lt;br /&gt;Digital media while offering convenient method of publication and spreading with minimum logistic cost. They are intangible. Consumer doesn’t feel they ‘own’ it. &lt;a href="http://www.delicious-monster.com/"&gt;Delicious Library&lt;/a&gt; offers a revolution way to materialize the electron to give user a feel of ownership.&lt;br /&gt;&lt;br /&gt;This brings me to think how we could use internet as ‘WEB’ – meaning all information are linked and not isolated. In aspect of digital music, book collections, there is a clear advantage over the tradition tangible collections. You can easily share or show off your collection worldwide.&lt;br /&gt;&lt;br /&gt;We are not talking about Napster, but the book list or music play list. Or even better your book review critics.&lt;br /&gt;&lt;br /&gt;I am talking about a WWW portable collection of your participation. A hybrid of webblog, Amazon, iTune, Delicious library and Opac or even more. Say, you write reviews on the books you read recently. You have a collection of the critics online that says everything about you – (‘&lt;em&gt;I think therefore I am&lt;/em&gt;’?) Your collection is also fed to community forums (BBS, Amazon etc) so it is cross referenced.&lt;br /&gt;&lt;br /&gt;Would this model gives a feeling of ownership of intangible?&lt;br /&gt;&lt;br /&gt;&lt;a href="http://arstechnica.com/reviews/apps/delicious-library.ars"&gt;Delicious Library Review&lt;/a&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-112172461633014191?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/112172461633014191/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=112172461633014191' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/112172461633014191'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/112172461633014191'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2005/07/delicious-library-and-more.html' title='Delicious Library and more'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-112141533748657492</id><published>2005-07-15T09:02:00.000+01:00</published><updated>2006-11-01T12:13:12.966Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='not work'/><title type='text'>Get Things Done</title><content type='html'>&lt;a href="http://www.minezone.org/wiki/MVance/GettingThingsDone"&gt;This bullet point article&lt;/a&gt; giev some very useful advice on time &amp;amp; project management.&lt;br /&gt;&lt;br /&gt;In my experience, in eXtreme programming one of the pain and time-consuming task is project planning: ask business partners to define the requirements and prioritised them with full house of the team sitting around – project managers, developers, testers and etc. Some people loss their interest in this lengthy meetings because on&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-112141533748657492?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='related' href='http://www.minezone.org/wiki/MVance/GettingThingsDone' title='Get Things Done'/><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/112141533748657492/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=112141533748657492' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/112141533748657492'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/112141533748657492'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2005/07/get-things-done.html' title='Get Things Done'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-111809845746771716</id><published>2005-06-07T12:38:00.000+01:00</published><updated>2006-11-01T12:14:37.158Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='SOA'/><title type='text'>SOA: what people said about it</title><content type='html'>Grady &lt;a href="http://www-106.ibm.com/developerworks/blogs/dw_blog_comments.jspa?blog=317&amp;amp;entry=65585"&gt;points&lt;/a&gt; out SOA is just &lt;strong&gt;one part&lt;/strong&gt;of establishing an enterprise architecture. The solid software engineering is still required.&lt;br /&gt;He also argues that SOA is for 'large grained/low frequency interactions'. This is controversial. As Jim Alateras &lt;a href="http://www.oreillynet.com/pub/wlg/6605"&gt;points out&lt;/a&gt; in his blog, B2C sites like ebay, amazon are SOA-ed. SOA brings architectural sound WEB API, it also enables a core infrastructure stack to support multiple channels, such like smart client.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-111809845746771716?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='related' href='http://www-106.ibm.com/developerworks/blogs/dw_blog_comments.jspa?blog=317&amp;entry=65585' title='SOA: what people said about it'/><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/111809845746771716/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=111809845746771716' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/111809845746771716'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/111809845746771716'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2005/06/soa-what-people-said-about-it.html' title='SOA: what people said about it'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-111809734253148959</id><published>2005-06-06T23:24:00.000+01:00</published><updated>2006-11-01T12:15:14.413Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='asp.net'/><title type='text'>What Great .NET Developers Ought To Know (Part Four ASP.NET (UI) Developers)</title><content type='html'>&lt;strong&gt;Part Four ASP.NET (UI) Developers (III)&lt;/strong&gt;&lt;br /&gt;&lt;strong&gt;Describe ways to present an arbitrary endpoint (URL) and route requests to that endpoint to ASP.NET.&lt;/strong&gt;&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;Explain how cookies work. Give an example of Cookie abuse.&lt;br /&gt;&lt;/strong&gt;Cookie is a text file has a name, contains a collection of values, and an expiration time. Cookie is planted to client browser by a web server. It contains value that can be used by the server to identify a client later.&lt;br /&gt;Cookie abuse means a web contain provider using cookie to collect personal/demographic information without prior consent from the user and/or use these data in a way without user consent. Here is an example: &lt;a href="http://www.theregister.co.uk/2000/01/28/doubleclick_sued_over_alleged_cookie/"&gt;Doubleclick sued over alleged cookie abuse&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;Explain the importance of HttpRequest.ValidateInput()? &lt;/strong&gt;&lt;br /&gt;ValidateInput check the three collections (QueryString, Form, and Cookies) for markup tags to prevent potentially dangerous data like &lt;a href="http://www.dwheeler.com/secure-programs/Secure-Programs-HOWTO/cross-site-malicious-content.html"&gt;cross site scripting&lt;/a&gt;.&lt;br /&gt;If the validation feature is enabled by page directive or configuration, this method is called during the Page's ProcessRequest processing phase. ValidateInput can be called by your code if the validation feature is not enabled. Request validation works by checking all input data against a hard-coded list of potentially dangerous data.&lt;br /&gt;QueryString, Form, and Cookies input data is checked during request validation.&lt;br /&gt;&lt;div class="code" id="divValidationReq1"&gt;&amp;lt;%@ Page validation="true" /“false” %&amp;gt;&lt;/div&gt;&lt;br /&gt;&lt;strong&gt;What kind of data is passed via HTTP Headers? &lt;/strong&gt;&lt;br /&gt;HTTP header metadata (information) about the document (HTML). Standard ones like:&lt;br /&gt;&lt;br /&gt;&lt;div class="code" id="divHttpHeader"&gt;HTTP/1.1 200 OK&lt;br /&gt;Date: Wed, 13 Aug 1997 02:35:50 GMT&lt;br /&gt;Server: Apache/1.2.0&lt;br /&gt;Last-Modified: Fri, 04 Jul 1997 22:18:24 GMT&lt;br /&gt;ETag: "28f7d-810-33bd76b0"&lt;br /&gt;Content-Length: 2064&lt;br /&gt;Accept-Ranges: bytes&lt;br /&gt;Connection: close&lt;br /&gt;Content-Type: text/html&lt;/div&gt;&lt;br /&gt;One can also define additional metadata like:&lt;br /&gt;&lt;div class="code" id="divValidationReq2"&gt;&amp;lt;META HTTP-EQUIV="Author" CONTENT="John Doe"&amp;gt;&lt;/div&gt;When the browser gets the document, it pretends that there is a header looks like this:&lt;br /&gt;&lt;div class="code" id="divValidationReq3"&gt;Author: John Doe&lt;/div&gt;&lt;br /&gt;Pointers &lt;a href="http://www.cs.tut.fi/%7Ejkorpela/http.html"&gt;Quick reference to HTTP headers&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;Juxtapose the HTTP verbs GET and POST. What is HEAD? &lt;/strong&gt;&lt;br /&gt;&lt;strong&gt;HTTP-GET&lt;/strong&gt; request gets information from a web server. It passes arguements (querystring) as a part of hostname via URL. Total length is limited a few hundred bytes. &lt;strong&gt;HTTP-POST&lt;/strong&gt; request allows a client to send data to the server. The POST method passes all of its parameter data in an input stream, removing the limit of the size of the data. Unlike the GET method, POST is &lt;em&gt;not expected&lt;/em&gt; to be safe nor idempotent&lt;br /&gt;The &lt;strong&gt;HTTP HEAD&lt;/strong&gt; method is very similar to the HTTP GET method. The request looks exactly the same as the GET request (except the word HEAD is used instead of GET), but the server only returns the header information.&lt;br /&gt;HEAD is often used to check the following:&lt;br /&gt;&lt;span style="font-size:85%;"&gt;   The last-modified date of a document on the server for caching purposes&lt;br /&gt;  The size of a document before downloading (so the browser can present progress information)&lt;br /&gt;  The server type, allowing the client to customize requests for that server&lt;br /&gt;  The type of the requested document, so the client can be sure it supports it&lt;br /&gt;&lt;/span&gt;Note that HEAD, like GET, is expected to be&lt;em&gt; safe&lt;/em&gt; and &lt;em&gt;idempotent&lt;/em&gt;.&lt;br /&gt;A practical use of HEAD is to scan massive URLs for validity or search stream files (MP3 search engine) in which we need retrieve only part of a file which contains the descriptor fields (metadata).&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;Name and describe at least a half dozen HTTP Status Codes and what they express to the requesting client. &lt;/strong&gt;&lt;br /&gt;1XX: informational:&lt;br /&gt;100: Continue; 101: Switch protocols&lt;br /&gt;2XX: Sucessful:&lt;br /&gt;200: OK; 201 Created; 202 Accepted&lt;br /&gt;3XX: Redirection&lt;br /&gt;300 Multiple Choices; 301 Moved Permanently; 302: Redirect request found;&lt;br /&gt;4XX: Client Error&lt;br /&gt;400: Bad request; 401:Unauthorized; 403: Forbidden; 404: Resource Not Found;&lt;br /&gt;5XX: Server Error&lt;br /&gt;500: Internal Server Error; 501 Not Implemented; 502 Bad Gateway; 503 Service Unavailable.&lt;br /&gt;Pointer&lt;br /&gt;Hypertext Transfer Protocol -- HTTP/1.1 RFC 2616 Fielding, et al. &lt;a href="http://www.w3.org/Protocols/rfc2616/rfc2616-sec10.html"&gt;Status Code Definitions&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;How does&lt;/strong&gt; If-Unmodified-Since  &lt;strong&gt;work? How can it be programmatically implemented with ASP.NET?&lt;/strong&gt;&lt;br /&gt;The If-Unmodified-Since request-header field is used with a method to make it conditional. If the requested resource has not been modified since the time specified in this field, the server SHOULD perform the requested operation as if the If-Unmodified-Since header were not present.&lt;br /&gt;&lt;br /&gt;&lt;a href="http://www.devx.com/dotnet/Article/22533/1954?pf=true"&gt;Tracking and Resuming Large File Downloads&lt;/a&gt; gives a nice clean example on a file download HttpHandler implementation. In the ProcessRequest method it checks HTTP headers to decide the download status.&lt;br /&gt;&lt;div id="divIfUnmodified1" class="code"&gt;...&lt;br /&gt;   ElseIf Not CheckIfUnmodifiedSince(objRequest, _&lt;br /&gt;     objFile) Then&lt;br /&gt;     ' The entity was modified since the requested&lt;br /&gt;     ' date...&lt;br /&gt;     objResponse.StatusCode = 412  ' Precondition failed&lt;br /&gt;&lt;br /&gt; Private Function CheckIfUnmodifiedSince(ByVal objRequest As HttpRequest, ByVal objFile As Download.FileInformation) As Boolean&lt;br /&gt;   Dim sDate As String&lt;br /&gt;   Dim dDate As Date&lt;br /&gt;   Dim bReturn As Boolean&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;   ' Checks the If-Unmodified or Unless-Modified-Since header, if&lt;br /&gt;   ' one of them was sent with the request.&lt;br /&gt;   '&lt;br /&gt;   ' Returns True, if the file was not modified since the&lt;br /&gt;   '               indicated date (RFC 1123 format), or&lt;br /&gt;   '               if no header was sent,&lt;br /&gt;   ' returns False, if the file was modified since the indicated date&lt;br /&gt;   ' Retrieve If-Unmodified-Since Header value from Request (Empty if none is indicated)&lt;br /&gt;   sDate = RetrieveHeader(objRequest, "If-Unmodified-Since"&lt;br /&gt;, String.Empty)&lt;br /&gt;&lt;br /&gt;   If sDate.Equals(String.Empty) Then&lt;br /&gt;     ' If-Unmodified-Since was not sent, check Unless-Modified-Since...&lt;br /&gt;     sDate = RetrieveHeader(objRequest, HTTP_HEADER_UNLESS_MODIFIED_SINCE, String.Empty)&lt;br /&gt;   End If&lt;br /&gt;   If sDate.Equals(String.Empty) Then&lt;br /&gt;     ' No date was indicated,&lt;br /&gt;     ' so just give this as True&lt;br /&gt;     bReturn = True&lt;br /&gt;…&lt;br /&gt;   End If&lt;br /&gt;   Return bReturn&lt;br /&gt; End Function&lt;/div&gt;&lt;br /&gt;Pointers &lt;a href="http://www.cs.tut.fi/%7Ejkorpela/http.html"&gt;Quick reference to HTTP headers&lt;/a&gt; &lt;a href="http://www.devx.com/dotnet/Article/22533/1954?pf=true"&gt;Tracking and Resuming Large File Downloads&lt;/a&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-111809734253148959?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/111809734253148959/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=111809734253148959' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/111809734253148959'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/111809734253148959'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2005/06/what-great-net-developers-_111809734253148959.html' title='What Great .NET Developers Ought To Know (Part Four ASP.NET (UI) Developers)'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-111808363349911490</id><published>2005-06-06T19:46:00.000+01:00</published><updated>2006-11-01T12:15:43.208Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='asp.net'/><title type='text'>What Great .NET Developers Ought To Know (Part Four ASP.NET (UI) Developers)</title><content type='html'>&lt;strong&gt;Part Four ASP.NET (UI) Developers (II)&lt;/strong&gt;&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;Give an example of how using an HttpHandler could simplify an existing design that serves Check Images from an .aspx page.&lt;/strong&gt;&lt;br /&gt;Scot Hanselman himself got something to say on &lt;a href="http://www.hanselman.com/blog/ABoilerplateHttpHandler.aspx"&gt;A Boilerplate HttpHandler&lt;/a&gt;.&lt;br /&gt;Just like .aspx page is an HttpHandler that handles Http Request:&lt;br /&gt;&lt;div class="code" id="divHttpHandler1"&gt;// System.Web.UI.Page&lt;br /&gt;public class Page : TemplateControl, IHttpHandler&lt;br /&gt;&lt;br /&gt;&amp;lt;httphandlers&amp;gt;&lt;br /&gt;...&lt;br /&gt;&amp;lt;add type="System.Web.UI.PageHandlerFactory" path="*.aspx" verb="*"&amp;gt;&lt;br /&gt;...&lt;br /&gt;&amp;lt;/httphandlers&amp;gt;&lt;/div&gt;&lt;br /&gt;You can implement your own HttpHandler to return other MEMI type (image, download file, pdf etc) to browser. The register your HttpHandler in the web.config (or you can register it in machine.config or IIS Application Configuration properties page if implements &lt;a href="http://msdn.microsoft.com/library/en-us/cpref/html/frlrfSystemWebIHttpHandlerFactoryClassTopic.asp"&gt;IHttpHandlerFactory&lt;/a&gt;)&lt;br /&gt;&lt;div class="code" id="divHttpHander2"&gt;//my HttpHandler&lt;br /&gt;public class MyHandler : IHttpHandler{…}&lt;br /&gt;&amp;lt;configuration&amp;gt;&lt;br /&gt;&amp;lt;system.web&amp;gt;&lt;br /&gt;&amp;lt;httphandlers&amp;gt;&lt;br /&gt;&amp;lt;add type="Namespace.MyHandler.New, MyHandlerAssemblyName" path="MyHandler.New" verb=" GET, PUT, POST "&amp;gt;&lt;br /&gt;&amp;lt;/httphandlers&amp;gt;&lt;/div&gt;&lt;br /&gt;MyHandler implementation (primarily in ProcessRequest)should cater following steps:&lt;br /&gt;1 Setting con&lt;span style="font-family:courier new;"&gt;text.Response.StatusCode &lt;/span&gt;&lt;br /&gt;2 Setting &lt;span style="font-family:courier new;"&gt;context.Response.ContentType = "somespecific/mimetype"; &lt;/span&gt;(e.g. Image/jpg)&lt;br /&gt;3 Setting &lt;span style="font-family:courier new;"&gt;context.Response&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;What kinds of events can an HttpModule subscribe to? What influence can they have on an implementation? What can be done without recompiling the ASP.NET Application?&lt;/strong&gt;&lt;br /&gt;An HttpModule implement IHttpModule:&lt;br /&gt;&lt;div class="code" id="divHttpModule1"&gt;public interface IHttpModule{&lt;br /&gt;void Dispose();&lt;br /&gt;void Init(HttpApplication context)&lt;br /&gt;}&lt;/div&gt;&lt;br /&gt;HttpModules are hooked into the Http request pipeline via entry like this in web.config:&lt;br /&gt;&lt;div class="code" id="divHttpModule2"&gt;&lt;configuration&gt;&lt;system.web&gt;&amp;lt;httpmodules&amp;gt;&lt;br /&gt;&amp;lt;configuration&amp;gt;&amp;lt;system.web&amp;gt;&amp;lt;/a&amp;gt;&amp;lt;httpmodules&amp;gt;&lt;br /&gt;&amp;lt;add type="classname,assemblyname" name="modulename"&amp;gt;&amp;lt;remove name="modulename"&amp;gt;&lt;br /&gt;&amp;lt;clear&amp;gt;&lt;br /&gt;&amp;lt;/httpmodules&amp;gt;&lt;/system.web&gt;&lt;/configuration&gt;&lt;/div&gt;&lt;br /&gt;The ASP.NET runtime calls the module's Init and Dispose methods. Init is called when the module attaches itself to the HttpApplication object and Dispose is called when the module is detached from &lt;span style="font-family:courier new;"&gt;HttpApplication&lt;/span&gt;. The Init and Dispose methods represent the module's opportunity to hook into a variety of events exposed by &lt;span style="font-family:courier new;"&gt;HttpApplication&lt;/span&gt;.&lt;br /&gt;&lt;br /&gt;As can be seen from the above config settings, without recompile the asp.net app, you can remove one or more HttpModules.&lt;br /&gt;&lt;br /&gt;An HttpMoudle can subscribe to following events:&lt;br /&gt;&lt;strong&gt;AcquireRequestState&lt;/strong&gt; When ASP.NET acquires the current state (for example, session state) associated with the current request.&lt;br /&gt;&lt;strong&gt;AuthenticateRequest&lt;/strong&gt; When a security module has established the identity of the user&lt;br /&gt;&lt;strong&gt;AuthorizeRequest&lt;/strong&gt; When a security module has verified user authorization&lt;br /&gt;&lt;strong&gt;BeginRequest&lt;/strong&gt; When the first event in the HTTP pipeline chain of execution responds to a request&lt;br /&gt;&lt;strong&gt;Disposed&lt;/strong&gt; When ASP.NET completes the chain of execution when responding to a request&lt;br /&gt;&lt;strong&gt;EndRequest&lt;/strong&gt; When the last event in the HTTP pipeline chain of execution responds to a request&lt;br /&gt;&lt;strong&gt;Error&lt;/strong&gt; When an unhandled exception is thrown&lt;br /&gt;&lt;strong&gt;PostRequestHandlerExecute&lt;/strong&gt; When the ASP.NET handler (page, XML Web Service) finishes execution&lt;br /&gt;&lt;strong&gt;PreRequestHandlerExecute&lt;/strong&gt; Just before ASP.NET begins executing a handler such as a page or XML Web Service&lt;br /&gt;&lt;strong&gt;PreSendRequestContent&lt;/strong&gt; Just before ASP.NET sends content to the client&lt;br /&gt;&lt;strong&gt;PreSendRequestHeaders&lt;/strong&gt; Just before ASP.NET sends HTTP headers to the client&lt;br /&gt;&lt;strong&gt;ReleaseRequestState&lt;/strong&gt; After ASP.NET finishes executing all request handlers; also causes state modules to save the current state data&lt;br /&gt;&lt;strong&gt;ResolveRequestCache&lt;/strong&gt; When ASP.NET completes an authorization event to let the caching modules serve requests from the cache, bypassing execution of the handler (the page or XML Web Service, for example)&lt;br /&gt;&lt;strong&gt;UpdateRequestCache&lt;/strong&gt; When ASP.NET finishes executing a handler in order to let caching modules store responses that will be used to serve subsequent requests from the cache&lt;br /&gt;&lt;br /&gt;A sample HttpModule class: &lt;div class="code" id="divHttpModule1"&gt;&lt;br /&gt;// This module, named HttpModules.CS will be compiled&lt;br /&gt;// into an assembly named HttpModules.dll&lt;br /&gt;// config entry:&lt;br /&gt;// &amp;lt;add type=" HttpModuleExamples.CustomHttpModule, HttpModules.dll" name=" CustomHttpModule"&amp;gt;&lt;br /&gt;&lt;br /&gt;using System;&lt;br /&gt;using System.Web;&lt;br /&gt;&lt;br /&gt;namespace HttpModuleExamples {&lt;br /&gt;public class CustomHttpModule : IHttpModule {&lt;br /&gt;// IHttpModule members&lt;br /&gt;public void Init(HttpApplication httpApp) {&lt;br /&gt;httpApp.BeginRequest +=&lt;br /&gt;new EventHandler(this.OnBeginRequest);&lt;br /&gt;&lt;br /&gt;httpApp.EndRequest +=&lt;br /&gt;new EventHandler(this.OnEndRequest);&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;public void Dispose() {&lt;br /&gt;// Usually, nothing has to happen here...&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;// event handlers&lt;br /&gt;public void OnBeginRequest(object o, EventArgs ea) {&lt;br /&gt;HttpApplication httpApp = (HttpApplication) o;&lt;br /&gt;HttpContext ctx = HttpContext.Current;&lt;br /&gt;ctx.Response.Write("Beginning Request&lt;br /&gt;");&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;public void OnEndRequest(object o, EventArgs ea) {&lt;br /&gt;HttpApplication httpApp = (HttpApplication) o;&lt;br /&gt;HttpContext ctx = HttpContext.Current;&lt;br /&gt;&lt;br /&gt;ctx.Response.Write("Ending Request&lt;br /&gt;");}}}&lt;/div&gt;&lt;br /&gt;&lt;br /&gt;Pointer: &lt;a href="http://msdn.microsoft.com/msdnmag/issues/02/05/asp/"&gt;HTTP Modules&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;Explain &lt;@OutputCache%&gt; and the usage of VaryByParam, VaryByHeader, VaryByCustom?&lt;/strong&gt;&lt;br /&gt;&amp;lt;@OutputCache%&amp;gt; Declaratively controls the output caching policies of an ASP.NET page or a user control contained in a page. Cached page/control is placed in memory.&lt;br /&gt;VaryByParam: Different versions of the page are stored based on the query string values.&lt;br /&gt;&lt;br /&gt;If there are one thousand different ids are queried in 30 sec, there will be one thousand pages cached. On the other hand queries page.aspx?id=1, page.aspx?id=1&amp;Num=1, and page.aspx?id=1&amp;amp;Num=2 will receive the same cached page.&lt;br /&gt;VaryByHeader: Different versions of the page are stored based on the specified HTTP header values.&lt;br /&gt;&lt;br /&gt;Four requests arrive for the page with the following Accept-Language headers: 1) de-lu; 2) en-us; 3) fr; 4) en-us, three cached pages is created and the second en-us request reads from cache.&lt;br /&gt;VaryByCustom: Different versions of the page are stored based on browser type and major version. Additionally, you can extend output caching by defining custom strings.&lt;br /&gt;&lt;br /&gt;Then override the HttpApplication.GetVaryByCustomString method in the Global.asax file. This string is built by you and used as a key to store and retrieve a cached version of your page. The key can be anything and build from anything. You can create a composite key from other pieces of information available to you like cookies, user-languages, browser capabilities, whatever.&lt;br /&gt;&lt;div class="code" id="divVaryByCustom1"&gt;&lt;br /&gt;public override string GetVaryByCustomString(HttpContext context, string arg){&lt;br /&gt;if(arg.ToLower() == "mycustomstring"){&lt;br /&gt;HttpCookie cookie = context.Request.Cookies["ID"];&lt;br /&gt;if(cookie != null)&lt;br /&gt;return cookie.Value;&lt;br /&gt;}&lt;br /&gt;return base.GetVaryByCustomString (context, custom);&lt;br /&gt;}&lt;/div&gt;&lt;br /&gt;Pointer: &lt;a href="http://www.hanselman.com/blog/AdvancedASPNETCachingAndAddValidationCallBack.aspx"&gt;Advanced ASP.NET Caching and AddValidationCallBack&lt;/a&gt; &lt;a href="http://msdn.microsoft.com/library/default.asp?url=/library/en-us/dnpag/html/scalenetchapt06.asp"&gt;Improving ASP.NET Performance&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;How would one implement ASP.NET HTML output caching, caching outgoing versions of pages generated via all values of q= except where q=5 (as in http://localhost/page.aspx?q=5)&lt;/strong&gt;?&lt;br /&gt;Use &lt;a href="http://msdn.microsoft.com/library/default.asp?url=/library/en-us/cpref/html/frlrfSystemWebHttpCachePolicyClassAddValidationCallbackTopic.asp"&gt;AddValidationCallBack&lt;/a&gt; It provides a mechanism to programmatically check the validity of a item in the cache before the item is returned from the cache. Before the response is served from the Web server cache, all registered handlers are queried to ensure resource validity. If any handler sets a flag indicating that the resource is invalid, the entry is marked invalid and evicted from the cache. The request is then handled as if it were a cache miss.&lt;br /&gt;Pointer: &lt;a href="http://www.hanselman.com/blog/AdvancedASPNETCachingAndAddValidationCallBack.aspx"&gt;Advanced ASP.NET Caching and AddValidationCallBack&lt;/a&gt; &lt;a href="http://msdn.microsoft.com/library/default.asp?url=/library/en-us/cpref/html/frlrfSystemWebHttpCachePolicyClassAddValidationCallbackTopic.asp"&gt;MSDN AddValidationCallBack&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;When can I safely set the EnableViewState property to False?&lt;/strong&gt;&lt;br /&gt;Pointers: &lt;a href="http://msdn.microsoft.com/library/default.asp?url=/library/en-us/dnaspp/html/viewstate.asp"&gt;Understanding ASP.NET View State&lt;/a&gt;&lt;br /&gt;View state is only need when you need to remember state across postbacks.&lt;br /&gt;For a Web page that has a read-only DataGrid, you'd definitely want to set the DataGrid's EnableViewState property to False. You can even create sortable and pageable DataGrids with the view state disabled.&lt;br /&gt;&lt;br /&gt;The DataGrid stores its contents in the view state so the page developer doesn't need to rebind the database data to the DataGrid on each and every page load, but only on the first one. The benefit is that the database doesn't need to be accessed as often. If, however, you set a DataGrid's EnableViewState property to False, you'll need to rebind the database data to the DataGrid on both the first page load and every subsequent postback.&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;Using cookieless sessions is that the session state is lost if an absolute URL is invoked&lt;/strong&gt;(&lt;a href="http://msdn.microsoft.com/library/default.asp?url=/library/en-us/dnaspp/html/aspnetsessionstate.asp"&gt;Underpinnings of the Session State Implementation in ASP.NET&lt;/a&gt;)&lt;br /&gt;The context:&lt;br /&gt;Suppose that you request a page at the following URL:&lt;br /&gt;&lt;div class="code" id="cookieless1"&gt;http://www.contoso.com/sample.aspx&lt;/div&gt;&lt;br /&gt;What is really displayed in the browser's address bar is slightly different and now includes the session ID, as shown here:&lt;br /&gt;&lt;div class="code" id="cookieless2"&gt;http://www.contoso.com/(5ylg0455mrvws1uz5mmaau45)/sample.aspx&lt;/div&gt;&lt;br /&gt;When instantiated, the session-state HTTP module checks the value of the cookieless attribute. If true, the request is redirected (HTTP 302) to a modified virtual URL that includes the session ID just before the page name. When processed again, the request embeds the session ID. If the request starts a new session, the HTTP module generates a new session ID and then redirects the request. If the request is a postback, the session ID is already there because postbacks use relative URLs.&lt;br /&gt;&lt;br /&gt;The problem:&lt;br /&gt;The drawback of using cookieless sessions is that the session state is lost if an absolute URL is invoked. When cookies are used, you can clear the address bar, go to another application, and then return to the previous one and retrieve the same session values. If you do this when session cookies are disabled, the session data is lost. For example, the following code breaks the session:&lt;br /&gt;&lt;div class="code"&gt;&amp;lt;a href="/code/page.aspx" runat="server"&amp;gt;Click&amp;lt;/a&amp;gt;&lt;/div&gt;&lt;div class="code"&gt;&lt;/div&gt;&lt;br /&gt;The solution:&lt;br /&gt;If you need to use absolute URLs, resort to a little trick and manually add the session ID to the URL. You use the &lt;strong&gt;ApplyAppPathModifier&lt;/strong&gt; method on the &lt;strong&gt;HttpResponse&lt;/strong&gt; class.&lt;br /&gt;&lt;div id="divsession3" class="code"&gt;&amp;lt;a runat="server"&lt;br /&gt;href=&amp;lt;% =Response.ApplyAppPathModifier("/code/page.aspx")%&amp;gt; &amp;gt;Click&amp;lt;/a&amp;gt;&lt;/div&gt;&lt;br /&gt;The &lt;strong&gt;ApplyAppPathModifier&lt;/strong&gt; method takes a string representing a URL and returns an absolute URL, which embeds session information. For example, this trick is especially useful in situations in which you need to redirect from a HTTP page to an HTTPS page.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-111808363349911490?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/111808363349911490/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=111808363349911490' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/111808363349911490'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/111808363349911490'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2005/06/what-great-net-developers-_111808363349911490.html' title='What Great .NET Developers Ought To Know (Part Four ASP.NET (UI) Developers)'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-111804625776825798</id><published>2005-06-06T09:10:00.000+01:00</published><updated>2006-11-01T12:16:16.268Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='asp.net'/><title type='text'>What Great .NET Developers Ought To Know (Part Four ASP.NET (UI) Developers)</title><content type='html'>This is getting longer and longer. Some questions are rather like a small insight reseach than a simple Q&amp;A. I will re-org some of them later to be a stand alone post.&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;Part Four ASP.NET (UI) Developers (I)&lt;/strong&gt;&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;Describe how a browser-based Form POST becomes a Server-Side event like Button1_OnClick.&lt;/strong&gt;&lt;br /&gt;In Web server controls, certain events, typically click events, cause the form to be posted back to the server. An event is a message, "Button1_Click". The binding between the event message and a specific method — that is, an event handler — is done using an event delegate. In the following code snippet, an (object of) event delegate &lt;span style="font-family:courier new;"&gt;EventHandler&lt;/span&gt; is instantiated, it binds the event handler - &lt;span style="font-family:courier new;"&gt;btnNext_Click&lt;/span&gt; method to the event &lt;span style="font-family:courier new;"&gt;btnNext.Click&lt;/span&gt; (message).&lt;br /&gt;&lt;div class="code" id="divbtnClick1"&gt;// the binding&lt;br /&gt;private void InitializeComponent(){&lt;br /&gt;//&lt;br /&gt;this.Load += new System.EventHandler(this.Page_Load);&lt;br /&gt;this.btnNext.Click += new System.EventHandler(this.btnNext_Click);&lt;br /&gt;}&lt;br /&gt;// an event handler&lt;br /&gt;private void btnNext_Click(object sender, System.EventArgs e){}&lt;/div&gt;&lt;br /&gt;&lt;strong&gt;What is a PostBack?&lt;/strong&gt;&lt;br /&gt;Postback means a web page (contains web request) is submitted to itself on the web server. ASP.NET page object model uses PostBack on event handling.&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;What is ViewState? How is it encoded? Is it encrypted? Who uses ViewState?&lt;/strong&gt;&lt;br /&gt;VIEWSTATE is a set or string of encoded data stored in a hidden form field to to preserve data between round trips to and from the server. ViewState automatically preserves property values of the page, and the values of all controls on the page, between round trips. Data stored in VIEWSTATE is base-64 encoded.&lt;br /&gt;Pointers: &lt;a href="http://msdn.microsoft.com/library/default.asp?url=/library/en-us/dnaspp/html/viewstate.asp"&gt;Understanding ASP.NET View State&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;What is the &amp;lt;machinekey&amp;gt;element and what two ASP.NET technologies is it used for?&lt;/strong&gt;&lt;br /&gt;&lt;em&gt;Machine Authentication Check&lt;/em&gt;(MAC): Machine authentication checks are designed to ensure that the data received by a computer is the same data that it transmitted out. This can be done by using &amp;lt;machinekey&amp;gt;.&lt;br /&gt;&amp;lt;machinekey&amp;gt;configures key to use for encryption and decryption of forms authentication cookie data and view state data, and for verification of out-of-process session state identification. This section can be declared at the machine (machine.config), site, and application levels (web.config), but not at the subdirectory level.&lt;br /&gt;&lt;div class="code" id="divMachineKey1"&gt;&amp;lt;configuration&amp;gt;&amp;lt;system.web&amp;gt;&amp;lt;/a&amp;gt;&amp;lt;machinekey validation="SHA1\\MD53\\DES" decryptionkey="AutoGeneratevalue[,IsolateApps]" validationkey="AutoGeneratevalue[,IsolateApps]"&amp;gt;&lt;/div&gt;&lt;br /&gt;&lt;strong&gt;What three Session State providers are available in ASP.NET 1.1? What are the pros and cons of each?&lt;/strong&gt;&lt;br /&gt;&lt;div class="code"&gt;&amp;lt;sessionState mode="InProc StateServer SQLServer /&amp;gt; &lt;/div&gt;&lt;br /&gt;&lt;strong&gt;InProc&lt;/strong&gt; Session values are kept as live objects in the memory of the ASP.NET worker process (aspnet_wp.exe or w3wp.exe in Microsoft® Windows Server™ 2003). This is the default option.&lt;br /&gt;Pros: Fastest. Cons: Not scalable (web garden/farm); performance hit as memory required, state lives short, less robust.&lt;br /&gt;&lt;br /&gt;Pros on out-of-proc: fully scalable; state lives longer; protected against IIS and ASP.Net failure; Cons: Slower than InProc due to serialization and de-serialization to/from storage medium. StateServer add at least 15%, SQLServer add at least 25% performance drop compares to InProc).&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;StateServer&lt;/strong&gt; Session values are serialized and stored in the memory of a separate process (aspnet_state.exe). The process can also run on another machine.&lt;br /&gt;Pros: fastest Out-of-Proc solution; easy administration. Cons: not as fast as InProc; not as robust as SQLServer.&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;SQLServer&lt;/strong&gt; Session values are serialized and stored in a Microsoft® SQL Server™ table. The instance of SQL Server can run either locally or remotely.&lt;br /&gt;Pros: more robust than StateServer.&lt;br /&gt;Cons: Slowest.&lt;br /&gt;Pointers: &lt;a href="http://msdn.microsoft.com/library/default.asp?url=/library/en-us/dnaspp/html/aspnetsessionstate.asp"&gt;Underpinnings of the Session State Implementation in ASP.NET&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;What is Web Gardening? How would using it affect a design?&lt;br /&gt;&lt;/strong&gt;The ASP.NET process model helps enable scalability on multiprocessor computers by distributing work to several processes, one per CPU, each with processor affinity set to its CPU. This technique is called &lt;strong&gt;Web Gardening&lt;/strong&gt;. This technique is particularly useful for applications that rely extensively on external resources, for example: slow database server or calls COM objects that have external dependencies.&lt;br /&gt;&lt;br /&gt;Web gardening is not suitable for heavy stateful applications. Web gardening enables multiple worker processes (one per CPU participating in the web garden) to run at the same time. All processes will have their own copy of application state, in-process session state, ASP.NET cache, static data etc, and all that is needed to run applications. &lt;em&gt;The more stateful applications are, the more they risk to pay in terms of real performance of web gardening&lt;/em&gt;.&lt;br /&gt;&lt;br /&gt;Beyond the questions:&lt;br /&gt;The Web garden model is configurable through the&lt;span style="font-family:courier new;"&gt; &amp;lt;processmodel&amp;gt;&lt;/span&gt;section of the machine.config file.&lt;br /&gt;&lt;em&gt;&lt;/em&gt;&lt;br /&gt;&lt;em&gt;Notice that the &amp;lt;processmodel&amp;gt; section is the only configuration section that cannot be placed in an application-specific web.config file. This means that the Web garden mode applies to all applications running on the machine.&lt;br /&gt;&lt;/em&gt;&lt;br /&gt;However, by using the &amp;l;tlocation&amp;gt; node in the machine.config source, you can adapt machine-wide settings on a per-application basis.&lt;br /&gt;&lt;div class="code" id="divprocessmode1"&gt;&amp;lt;processmodel webgarden="[truefalse]" cpumask="[bit mask]"&amp;gt;&lt;/div&gt;&lt;br /&gt;Pointer: &lt;a href="http://msdn.microsoft.com/library/default.asp?url=/library/en-us/dnaspp/html/dngrfTheASPNETHTTPRuntime.asp"&gt;The ASP.NET HTTP Runtime&lt;/a&gt;&lt;br /&gt;&lt;strong&gt;Given one ASP.NET application, how many application objects does it have on a single proc box? A dual? A dual with Web Gardening enabled? How would this affect a design?&lt;/strong&gt;&lt;br /&gt;The term ‘Application object’ is vague here. If we are talking about ASP.NET worker process (aspnet_wp.exe or w3wp.exe) it is one per CPU. On a Dual CPU box without enabling web gardening, it is still one worker process. If web gardening is enabled for all CPUs, one worker process is created per CPU.&lt;br /&gt;&lt;br /&gt;If we are talking about &lt;strong&gt;HttpApplication&lt;/strong&gt; object here, it has nothing to do with number of the CPUs in a box. ASP.NET worker process creates a number of AppDomains, isolated by the virtual directory or web application. Each AppDomain has an HttpApplication object pool. An individual HttpApplication object is created to handle each simultaneous HTTP request. However number of the objects in the HttpApplication pool is not configurable. Neither number of AppDomains (sure too many active web apps on a box will slow it down).&lt;br /&gt;&lt;br /&gt;Pointer &lt;a href="http://msdn.microsoft.com/library/default.asp?url=/library/en-us/dnnetsec/html/SecNetAP04.asp"&gt;Building Secure ASP.NET Applications: Authentication, Authorization, and Secure Communication&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;Are threads reused in ASP.NET between reqeusts? Does every HttpRequest get its own thread? Should you use Thread Local storage with ASP.NET?&lt;/strong&gt;&lt;br /&gt;Aha, just partly answered this question above. Each HTTP request is served by an HttpApplication object, which is pooled. Threads are reused.&lt;br /&gt;&lt;strong&gt;Thread Local storage(TLS) &lt;/strong&gt;provides a mechanism to store data that is unique to a thread and whose value is determined at run time. This type of storage can be very helpful when dealing with an existing multithreaded application whose interfaces or original design are too inflexible for passing these values another way.&lt;br /&gt;Using TLS in a thread pooling environment can be very tricky. One should not use TLS on ASP.NET application. You never know on what thread you might be called (inside an ISAPI DLL), so using TLS for anything other than tracking resources that are explicitly bound to a particular thread is a bad idea.&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;Is the [ThreadStatic] attribute useful in ASP.NET? Are there side effects? Good or bad?&lt;/strong&gt;&lt;br /&gt;&lt;a href="http://groups-beta.google.com/group/microsoft.public.dotnet.framework.aspnet/browse_frm/thread/cef5d88a2e3e26e1/85798178bdf7c0c8?q=asp.net+thread+agile&amp;amp;rnum=1#85798178bdf7c0c8"&gt;The conext&lt;/a&gt;: how to share static fields on per thread scope in opposite to per AppDomain scope?&lt;br /&gt;The question itself doesn't make sense. The value that needs to be shared should be tied to a specific request, not a specific thread. To do this you can use the &lt;span style="font-family:courier new;"&gt;&lt;strong&gt;System.Web.HttpContext.Current.Items&lt;/strong&gt;&lt;/span&gt; collection.&lt;br /&gt;&lt;strong&gt;[ThreadStatic]&lt;/strong&gt; is the managed equivalent of TLS in ASP.NET. It should be used when you can control the threadpool and the lifecycle of a thread (but you can’t achieve this easily, can you?) ThreadStatic gives you &lt;strong&gt;thread local storage&lt;/strong&gt;, not &lt;strong&gt;HttpContext local storage&lt;/strong&gt;!&lt;br /&gt;It needs to be very careful on using &lt;strong&gt;[ThreadStatic]&lt;/strong&gt; . Static fields marked with &lt;span style="font-family:courier new;"&gt;ThreadStaticAttribute&lt;/span&gt; are not shared between threads. Each executing thread has a separate instance of the field, and independently sets and gets values for that field. If the field is accessed on a different thread, it will contain a different value. And this is deemed to happen due to &lt;strong&gt;&lt;em&gt;thread agile&lt;/em&gt;&lt;/strong&gt; in ASP.NET. ASP.NET not only uses a thread pool, but may switch threads during request processing. It makes thread local storage unreliable.&lt;br /&gt;Pointers &lt;a href="http://www.hanselman.com/blog/StoringThingsOnThreads.aspx"&gt;Storing things on Threads&lt;/a&gt;, &lt;a href="http://www.hanselman.com/blog/ATaleOfTwoTechniquesTheThreadStaticAttributeAndSystemWebHttpContextCurrentItems.aspx"&gt;A tale of two techniques: The [ThreadStatic] Attribute and System.Web.HttpContext.Current.Items&lt;/a&gt;, &lt;a href="http://integralpath.blogs.com/thinkingoutloud/2005/03/threadstatic_fu.html"&gt;ThreadStatic FUD&lt;/a&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-111804625776825798?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='related' href='http://www.hanselman.com/blog/WhatGreatNETDevelopersOughtToKnowMoreNETInterviewQuestions.aspx' title='What Great .NET Developers Ought To Know (Part Four ASP.NET (UI) Developers)'/><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/111804625776825798/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=111804625776825798' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/111804625776825798'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/111804625776825798'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2005/06/what-great-net-developers-ought-to_06.html' title='What Great .NET Developers Ought To Know (Part Four ASP.NET (UI) Developers)'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-111788999057617320</id><published>2005-06-03T13:51:00.000+01:00</published><updated>2006-11-01T12:16:46.558Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='asp.net'/><title type='text'>What Great .NET Developers Ought To Know (Part Three C# Component Developers)</title><content type='html'>Continue on Scott Hanselman's - &lt;a href="http://www.hanselman.com/blog/WhatGreatNETDevelopersOughtToKnowMoreNETInterviewQuestions.aspx"&gt;What Great .NET Developers Ought To Know&lt;/a&gt;&lt;br /&gt;&lt;strong&gt;Part Three C# Component Developers&lt;/strong&gt;&lt;br /&gt;&lt;strong&gt;&lt;/strong&gt;&lt;br /&gt;&lt;br /&gt;&lt;p align="left"&gt;&lt;strong&gt;Juxtapose the use of override with new. What is shadowing?&lt;br /&gt;&lt;/strong&gt;Using &lt;span style="font-family:courier new;"&gt;override&lt;/span&gt; keyword to a method in the derived class meaning the method provides a new implementation to the overridden method (same signature) in the base class. The base method must be &lt;span style="font-family:courier new;"&gt;virtual, abstract&lt;span style="font-family:verdana;"&gt;, or&lt;/span&gt; override&lt;/span&gt;.&lt;br /&gt;By default a method is not modified by ‘virtual’. So if a method in derived class wants to override the base implementation, it needs to be modified by ‘new’ keyword.&lt;br /&gt;This is called &lt;strong&gt;shadowing&lt;/strong&gt;, not overriding. The method in the derived HIDES the one in the base class.&lt;/p&gt;&lt;p align="left"&gt;&lt;strong&gt;Explain the use of virtual, sealed, override, and abstract. &lt;/strong&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;&lt;strong&gt;virtual&lt;/strong&gt;&lt;/span&gt; keyword is used to modify a method or property declaration. It allows the &lt;strong&gt;downcasting&lt;/strong&gt; from base class to derived class. From derived class’s point, the method overrides it specialised the implementation. To enforce the overriding, base method modify with abstract.&lt;br /&gt;&lt;strong&gt;&lt;span style="font-family:courier new;"&gt;abstract&lt;/span&gt;&lt;/strong&gt; keyword is used to modify a class, method or property declaration. You cannot instantiate an abstract class or make calls to an abstract method directly.&lt;br /&gt;An &lt;strong&gt;&lt;span style="font-family:courier new;"&gt;abstract vir&lt;/span&gt;tual&lt;/strong&gt; method meaning that the method provides maybe a partial implementation, may be no implementation at all. And a derived class of it must implement it.&lt;br /&gt;A &lt;strong&gt;&lt;span style="font-family:courier new;"&gt;sealed&lt;/span&gt;&lt;/strong&gt; class cannot be derived. This modifier is most likely used on a static class. An abstract class cannot be sealed.&lt;br /&gt;A sealed override method in a derived class prevent it being further overriden.&lt;/p&gt;&lt;p align="left"&gt;&lt;strong&gt;Explain the importance and use of each component of this string: Foo.Bar, Version=2.0.205.0, Culture=neutral, PublicKeyToken=593777ae2d274679d&lt;br /&gt;&lt;/strong&gt;This string specifies shows a fully specified reference for a strongly named assembly.&lt;br /&gt;&lt;/p&gt;&lt;p align="left"&gt;&lt;strong&gt;Explain the differences between &lt;span style="font-family:courier new;"&gt;public, protected, private &lt;span style="font-family:verdana;"&gt;and&lt;/span&gt; internal&lt;/span&gt;.&lt;br /&gt;&lt;/strong&gt;Visibility differences on accessing a method, class:&lt;br /&gt;private methods are only visible to a member in the same class;&lt;br /&gt;protected methods are only visible to members in the derived class plus private scope;&lt;br /&gt;internal methods/classes are visible to members in the same assembly;&lt;br /&gt;public methods/class are visible to all. &lt;/p&gt;&lt;p align="left"&gt;&lt;strong&gt;What benefit do you get from using a Primary Interop Assembly (PIA)?&lt;br /&gt;&lt;/strong&gt;You get compatibility between applications that shares types defined in a PIA.&lt;br /&gt;&lt;a href="http://msdn.microsoft.com/library/default.asp?url=/library/en-us/dndotnet/html/whypriinterop.asp"&gt;PIA&lt;/a&gt; contains the official, unique type identity description as defined by the publisher of those types. The PIA may contain certain customizations that make the types easier to use from managed code. The PIA is always signed by the publisher of the original COM type.&lt;br /&gt;By what mechanism does NUnit know what methods to test?&lt;br /&gt;Reflection. &lt;/p&gt;&lt;p align="left"&gt;&lt;strong&gt;What is the difference between: catch(Exception e){throw e;} and catch(Exception e){throw;}&lt;/strong&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;catch(Exception e){throw e;}&lt;/span&gt; suppress the original exception stack and begin a new exception flow. Original stack trace information maybe lost&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;catch(Exception e){throw;}&lt;/span&gt; re-throw original exception. &lt;/p&gt;&lt;p align="left"&gt;&lt;strong&gt;What is the difference between typeof(foo) and myFoo.GetType()?&lt;br /&gt;&lt;/strong&gt;Operatior typeof(foo) is used to obtain the &lt;span style="font-family:courier new;"&gt;&lt;strong&gt;System.Type&lt;/strong&gt;&lt;/span&gt; object for a type at compile time.&lt;br /&gt;myFoo.GetType() is used to obtain the exact run time type of an object. This method uses reflection. &lt;/p&gt;&lt;p align="left"&gt;&lt;strong&gt;Explain what’s happening in the first constructor and h&lt;/strong&gt;&lt;strong&gt;ow is this construct useful?&lt;br /&gt;&lt;/strong&gt;&lt;br /&gt;&lt;/p&gt;&lt;div id="divcontor1" class="code"&gt;&lt;br /&gt;public class c{&lt;br /&gt;  public c(string a) : this() {;};&lt;br /&gt;  public c() {;}&lt;br /&gt;}&lt;/div&gt;&lt;br /&gt;When constructor public c(string a) is called to construct an object, it first calls the default constructor then the initialisation procedures in public c(string a). &lt;p&gt;&lt;/p&gt;&lt;p align="left"&gt;&lt;strong&gt;What is &lt;em&gt;this&lt;/em&gt;? Can this be used within a static method? &lt;/strong&gt;&lt;br /&gt;The this keyword refers to the current instance of the class. It cannot be use within a static method, because static method doesn’t live in an instance object type.&lt;/p&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-111788999057617320?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='related' href='http://www.hanselman.com/blog/WhatGreatNETDevelopersOughtToKnowMoreNETInterviewQuestions.aspx' title='What Great .NET Developers Ought To Know (Part Three C# Component Developers)'/><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/111788999057617320/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=111788999057617320' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/111788999057617320'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/111788999057617320'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2005/06/what-great-net-developers-ought-to_03.html' title='What Great .NET Developers Ought To Know (Part Three C# Component Developers)'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-111763244852482060</id><published>2005-06-01T14:25:00.000+01:00</published><updated>2006-11-01T12:17:42.975Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='not work'/><title type='text'>(Communication Skills)The Secret of Inspiration</title><content type='html'>&lt;span style="font-style: italic;"&gt;Wednesday June 1, 01:41 PM &lt;/span&gt;&lt;br /&gt;&lt;span style="font-style: italic;"&gt;The Secret of Inspiration &lt;/span&gt;&lt;br /&gt;&lt;span style="font-style: italic;"&gt;By Carmine Gallo &lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-style: italic;"&gt;During an interview for my new book, I was speaking to Dilbert creator Scott Adams about the failure of most managers to inspire their employees. Adams is very funny and extremely insightful. In his opinion, most business professionals fail to articulate Advertisement&lt;/span&gt;&lt;br /&gt; &lt;br /&gt;&lt;span style="font-style: italic;"&gt;a compelling vision because they don't have anything to say.&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-style: italic;"&gt;Simple enough and probably true in many cases. But if you're like most entrepreneurs, you do have something to say -- and a vision that will inspire your employees, colleagues, and customers. You might just need a little help getting it across.&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-style: italic;"&gt;Here's the deal: Most employees are uninspired by their work and by the people for whom they work. How do I know? Well, it doesn't take a rocket scientist. Just look at the face of the person next to you on the train during rush-hour commute. Pay attention to the bank teller's demeanor. Note the lack of enthusiasm from the department store sales clerk.&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-style: italic;"&gt;COMMON TECHNIQUES. A recent Conference Board survey finds that only half of U.S. workers are happy with their jobs, and of those who are happy, only 14% are "very satisfied." When people are uninspired at work, it shows -- customer-service surveys have revealed a marked decline in satisfaction in recent years.&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-style: italic;"&gt;My goal in writing 10 Simple Secrets of the World's Greatest Communicators was to identify business leaders who truly inspire those in their personal and professional lives, and to share their techniques with my readers. After interviewing more than two dozen contemporary CEOs, executives, and experts, I found a common technique among all those considered among the most inspiring. Are you ready for it? The secret to inspiring your listeners is to paint a picture of a world made better by your service, product, company, or cause.&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-style: italic;"&gt;Think about it. Cisco (CSCO) CEO John Chambers doesn't sell routers and switches when he communicates to employees, colleagues, or customers -- he sells a vision of an Internet that changes the way we "live, work, play, and learn." Starbucks (SBUX) founder Howard Schultz doesn't sell coffee beans -- he sells the concept of a community, a "third place" between work and home. Suze Orman doesn't sell irrevocable trusts -- she sells the vision of a life free of burdensome debt.&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-style: italic;"&gt;In much the same way, California Governor Arnold Schwarzenegger won the hearts and minds of voters not by outlining specific policies but by selling his vision of a state that's a better place to raise a family and do business.&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-style: italic;"&gt;"MAKING A DIFFERENCE." Intuit (INTU) founder Scott Cook told me, "It's important to communicate a bold vision for many reasons, but primarily for internal reasons, for the people in your company. Your people want to know that their work is adding up to a great cause. They want more than a paycheck. They want to know that they are making a difference in the world."&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-style: italic;"&gt;Are you communicating a bold, captivating vision? Do the people who work for you feel as though their work is adding up to more than a paycheck? Once they do, the results could be extraordinary. Remember the famous story of how Steve Jobs convinced former Pepsi (PEP) President John Scully to take the helm at Apple (AAPL)? On a balcony overlooking New York's Central Park, Jobs turned to Scully and asked, "Do you want to sell sugared water all your life, or do you want to change the world?"&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-style: italic;"&gt;It worked. In much the same way, articulating a big mission will help you win over employees, customers, and colleagues -- especially in a small business, where you can have direct and frequent contact with them.&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-style: italic;"&gt;WALK THROUGH FIRE? Last year, one of those traveling motivational conferences came rolling through my town in Silicon Valley. Its roster was made up of athletes, authors, and celebrities. I couldn't help but feel sorry for those business professionals who may have been fired up to do their best work by the end of the conference only to be deflated by their uninspiring supervisors the next day at the office.&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-style: italic;"&gt;CNBC money guru Jim Cramer once commented that people would walk through fire for Cisco's Chambers. Would they do the same for you? If not, why? Is it possible that you're failing to communicate the big mission behind your service, product, or company? In his autobiography, My American Journey, former Secretary of State Colin Powell writes that a great leader, "[makes] individuals feel important and part of something larger than themselves."&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-style: italic;"&gt;Sound familiar? The simple secret to inspiring those around you is to communicate a vision, a roadmap, of where you're heading and why it's important to your listeners. This technique applies to your conversations with employees, colleagues, customers, or investors.&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-style: italic;"&gt;START WITH YOURSELF. I hope I've already got you thinking about the mission you wish to convey. In my last column, I invited readers to share their "30-second pitch" with me (see BW Online, 5/4/05, "&lt;/span&gt;&lt;a style="font-style: italic;" href="http://businessweek.com/smallbiz/content/may2005/sb2005054_8868_sb037.htm"&gt;Mastering the 30-Second Pitch&lt;/a&gt;&lt;span style="font-style: italic;"&gt;"). Many of you responded. Well, this time I'm asking that you share your "big mission." Let me know how you've inspired those who work for you or how you plan to do so based on the above information. I would be happy to send you feedback.&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-style: italic;"&gt;But just one more thing before you head out to articulate your big mission. Suze Orman once told me that people can only inspire when they're inspired themselves. Good point. If you're not inspired by your own vision, then it might be time to reevaluate the road you're heading down. After all, if you're not out to change the world, plenty of others are.&lt;/span&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-111763244852482060?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='related' href='http://uk.biz.yahoo.com/050601/244/fk7gk.html' title='(Communication Skills)The Secret of Inspiration'/><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/111763244852482060/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=111763244852482060' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/111763244852482060'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/111763244852482060'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2005/06/communication-skillsthe-secret-of.html' title='(Communication Skills)The Secret of Inspiration'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-111758248690422935</id><published>2005-06-01T10:32:00.000+01:00</published><updated>2006-11-01T12:22:15.842Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='asp.net'/><title type='text'>What Great .NET Developers Ought To Know (Part Two Mid-Level .NET Developer)</title><content type='html'>&lt;p&gt;Continue on Scott Hanselman's - &lt;a href="http://www.hanselman.com/blog/WhatGreatNETDevelopersOughtToKnowMoreNETInterviewQuestions.aspx"&gt;What Great .NET Developers Ought To Know&lt;/a&gt;&lt;br /&gt;&lt;strong&gt;Part Two Mid-Level .NET Developer&lt;/strong&gt;&lt;/p&gt;&lt;br /&gt;&lt;p&gt;&lt;strong&gt;&lt;/strong&gt;&lt;/p&gt;&lt;li&gt;&lt;strong&gt;Describe the difference between Interface-oriented, Object-oriented and Aspect-oriented programming&lt;/strong&gt;&lt;br /&gt;&lt;strong&gt;Object-oriented programming (OOP): &lt;/strong&gt;a programming methodology built around data abstraction (i.e. type, class and object) and message communication between objects. The basic concepts of OOP are encapsulation, inheritance, and polymorphism.&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;Interface-oriented programming (IOP)&lt;/strong&gt; is an extension of OOP in which all program interdependencies are expressed via abstract interfaces. Abstract interfaces and implementations are strictly separated. As a result, inheritance in IOP is interface-oriented, supports both specialization and adaptation inheritance, and is decoupled from the implementation binding mechanism. (from &lt;a href="http://www.ii.uib.no/%7Emagne/stsw04-html-2/stsw04r-Varney-varneySTS.pdf"&gt;Generative Programming, Interface-Oriented Programming and Source Transformation Systems&lt;/a&gt;)&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;Aspect-oriented programming (AOP)&lt;/strong&gt; Eclipse Foundation defines AOP as: &lt;br /&gt;‘A type or style of programming that explicitly takes into account crosscutting concerns, just as object-oriented programming explicitly takes into account classes and objects.’&lt;br /&gt;&lt;br /&gt;The essence of AOP model is to identify concerns such as logging, exception handling, etc. that cross-cut several layers in a system, and modularise them into orthogonal units called &lt;strong&gt;aspects&lt;/strong&gt; and &lt;strong&gt;inject&lt;/strong&gt; these aspects at selected execution points in a system dynamically at runtime.&lt;br /&gt;&lt;u&gt;Pointers: Aspect Orienting .NET Components&lt;/u&gt;&lt;p&gt;&lt;/p&gt;&lt;br /&gt;&lt;p&gt;&lt;strong&gt;&lt;/strong&gt;&lt;/p&gt;&lt;/li&gt;&lt;li&gt;&lt;strong&gt;Describe what an Interface is and how it’s different from a Class&lt;/strong&gt;&lt;br /&gt;An interface defines a contract without implementation. A class can implement one or more interface. A class can only inherit one parent class. A interface can inherit many parent interfaces. There is no ‘implementation’ concept in interface. See this code snippet.&lt;br /&gt;&lt;div class="code" id="divInterface1"&gt;&lt;br /&gt;namespace ClassLibrary1{&lt;br /&gt; public interface IFace1{&lt;br /&gt;   void Foo1();&lt;br /&gt;   void Bar1();&lt;br /&gt; }&lt;br /&gt; public interface IFace3{&lt;br /&gt;   void Foo3();&lt;br /&gt; }&lt;br /&gt; public interface IFace2 : IFace1, IFace3{&lt;br /&gt;   void Foo2();&lt;br /&gt; }&lt;br /&gt; public class Class1 : IFace2{&lt;br /&gt; public Class1(){}&lt;br /&gt;&lt;br /&gt; // IFace2 Members&lt;br /&gt; public void Foo2(){}&lt;br /&gt;&lt;br /&gt; // IFace3 Members&lt;br /&gt; public void Foo3(){}&lt;br /&gt;&lt;br /&gt; // IFace1 Members&lt;br /&gt; public void Foo1(){}&lt;br /&gt; public void Bar1(){}&lt;br /&gt; }&lt;br /&gt;}&lt;br /&gt;&lt;/div&gt;&lt;p&gt;&lt;/p&gt;&lt;br /&gt;&lt;p&gt;&lt;strong&gt;&lt;/strong&gt;&lt;/p&gt;&lt;/li&gt;&lt;li&gt;&lt;strong&gt;What is Reflection?&lt;/strong&gt;&lt;br /&gt;When building an assembly or a module, the .NET compiler creates &lt;strong&gt;metadata&lt;/strong&gt; of the assembly at the same time. Metadata contains a type definition table, a field definition table, a module definition table etc. The process to query these metadata tables at runtime is called Reflection. The FCL’s System.Reflection namespace contains types a developer can use to write code to reflect metadata and obtain information about a type/class in the assembly, such like fields, methods, properties and events etc.&lt;p&gt;&lt;/p&gt;&lt;br /&gt;&lt;p&gt;&lt;strong&gt;&lt;/strong&gt;&lt;/p&gt;&lt;/li&gt;&lt;li&gt;&lt;strong&gt;What is the difference between XML Web Services using ASMX and .NET Remoting using SOAP?&lt;/strong&gt;&lt;br /&gt;Xml Web Services uses standard protocols such like HTTP, XML and SOAP in messaging. It addresses interoperability between disparate, heterogeneous   applications.&lt;br /&gt;The .NET Remoting system enables messaging between remote object across AppDomain, process or machine boundaries using communication channels like TCP/IP or HTTP. It doesn’t address interoperability between heterogeneous applications, meaning client and service object must expose/understand the communication interface – object reference.&lt;br /&gt;Message sent over communication channel is called remote object. Remote object is encoded/decoded using native .NET serialization formatters, such like binary or XML encoding like SOAP. Binary encoding is more efficient. XML encoding is preferred choice when interoperability is required.&lt;br /&gt;&lt;br /&gt;Some &lt;a href="http://blogs.crsw.com/mark/articles/253.aspx"&gt;brief Q&amp;As about Remoting&lt;/a&gt;.&lt;p&gt;&lt;/p&gt;&lt;br /&gt;&lt;p&gt;&lt;strong&gt;&lt;/strong&gt;&lt;/p&gt;&lt;/li&gt;&lt;li&gt;&lt;strong&gt;Are the type system represented by XmlSchema and the CLS isomorphic?&lt;/strong&gt;&lt;br /&gt;Isomorphic: In mathematics, an isomorphism (in Greek isos = equal and morphe = shape) is a kind of interesting mapping between objects. (&lt;a href="http://en.wikipedia.org/wiki/Isomorphic"&gt;Reference&lt;/a&gt;) Two isomorphic sets (such as species) have a one-to-one correspondence between them. For each member of one set, there is a corresponding member of the other set. For example, there is a one-to-one correspondence between the set of lower case letters and the set of upper case letters, with a corresponding to A, etc. (&lt;a href="http://www.cs.ecu.edu/%7Ekarl/astarte/glossary.html"&gt;Reference&lt;/a&gt;)&lt;br /&gt;.NET classes can be serialised into a XML Schema by using types in System.Xml.Serialization, such like XmlSerializer. (Some code example can be found  &lt;a href="http://www.awprofessional.com/articles/article.asp?p=29901&amp;amp;seqNum=3&amp;rl=1"&gt;here&lt;/a&gt;)&lt;br /&gt;CLS, Common Language Specification&lt;p&gt;&lt;/p&gt;&lt;br /&gt;&lt;p&gt;&lt;strong&gt;&lt;/strong&gt;&lt;/p&gt;&lt;/li&gt;&lt;li&gt;&lt;strong&gt;Conceptually, what is the difference between early-binding and late-binding?&lt;/strong&gt;&lt;br /&gt;Early-binding: static binding, validated by compiler. Late-binding: dynamic, type cast, validate by runtime.&lt;br /&gt;&lt;div id="divbinding1" class="code"&gt;&lt;br /&gt;public class Point{&lt;br /&gt; public Point(){&lt;br /&gt; }&lt;br /&gt; public int X = 0;&lt;br /&gt; public int Y = 0;&lt;br /&gt; }&lt;br /&gt; public class Line : Point{&lt;br /&gt; public Line(){&lt;br /&gt; }&lt;br /&gt;}&lt;br /&gt; public class Widget{&lt;br /&gt;  public Widget(){}&lt;br /&gt;}&lt;br /&gt; public class Foo{&lt;br /&gt;  Line line1 = null;&lt;br /&gt;  Widget widget = null;&lt;br /&gt;  Object object1 = null;&lt;br /&gt; &lt;br /&gt; public void Demo() {&lt;br /&gt;   //... do something with line1&lt;br /&gt;  &lt;br /&gt;   //early binding, complier will complain&lt;br /&gt;   Point p1 = (Point)line1;     &lt;br /&gt;   Console.Write("Location (X,Y) ({0}, {1})", p1.X, p1.Y);&lt;br /&gt; &lt;br /&gt;   //compiler complians on the cast&lt;br /&gt;   //Point p2 = (Point)widget;&lt;br /&gt;  &lt;br /&gt;   //late binding on a generic type&lt;br /&gt;   Point p3 = (Point)object1;&lt;br /&gt; &lt;br /&gt;   //following line only throws exception at runtime&lt;br /&gt;   Console.Write("Location (X,Y) ({0}, {1})", p3.X, p3.Y);&lt;br /&gt; }&lt;br /&gt;}&lt;br /&gt;&lt;/div&gt;&lt;p&gt;&lt;/p&gt;&lt;br /&gt;&lt;p&gt;&lt;strong&gt;&lt;/strong&gt;&lt;/p&gt;&lt;/li&gt;&lt;li&gt;&lt;strong&gt;Is using &lt;span style="font-family:courier new;"&gt;Assembly.Load&lt;/span&gt; a static reference or dynamic reference? What is an Asssembly Qualified Name? Is it a filename? How is it different? Is this valid? Assembly.Load("foo.dll"); When would using Assembly.LoadFrom or Assembly.LoadFile be appropriate? &lt;/strong&gt;&lt;br /&gt;&lt;/li&gt;&lt;li&gt;Using &lt;span style="font-family:courier new;"&gt;Assembly.Load(...)&lt;/span&gt; is a Dynamic Reference to load a type. The parameter can be an assembly qualified name (AQN, Type: string) like: ‘&lt;span style="font-family:courier new;"&gt;TopNamespace.SubNameSpace.ContainingClass+NestedClass,TheAssemblyName’&lt;/span&gt;.&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;Assembly.Load&lt;/span&gt; also accepts a simple assembly name, which must be an object of AssemblyName, for example:&lt;br /&gt;&lt;div class="Code" id="divAssemblyLoad1"&gt;&lt;br /&gt;AssemblyName myAssemblyName = new AssemblyName();&lt;br /&gt;myAssemblyName.Name = "MyAssembly";&lt;br /&gt;myAssemblyName.Version = new Version("1.0.0.2001");&lt;br /&gt;&lt;/div&gt;&lt;br /&gt;&lt;/li&gt;&lt;li&gt;&lt;span style="font-family:courier new;"&gt;‘foo.dll’&lt;/span&gt; is not a FQN, so &lt;span style="font-family:courier new;"&gt;Assembly.Load("foo.dll");&lt;/span&gt; is invalid.&lt;br /&gt;&lt;/li&gt;&lt;li&gt;An AQN contains an assembly’s identity information, such like:&lt;br /&gt;&lt;/li&gt;&lt;ul&gt;&lt;li&gt;A simple file name (unencrypted name);&lt;/li&gt;&lt;br /&gt;&lt;li&gt;A version number;&lt;/li&gt;&lt;br /&gt;&lt;li&gt;A cryptographic key pair;&lt;/li&gt;&lt;br /&gt;&lt;li&gt;And a supported culture. &lt;/li&gt;&lt;/ul&gt;&lt;br /&gt;It allows versioning and singing as opposed to a simple filename.&lt;br /&gt;&lt;li&gt;&lt;span style="font-family:courier new;"&gt;Assembly.LoadForm&lt;/span&gt;: Loads an assembly given its file name or path. &lt;span style="font-family:courier new;"&gt;Assembly.LoadFile&lt;/span&gt;: Loads the contents of an assembly file on the specified path. Use the LoadFile method to load and examine assemblies that have the same identity, but are located in different paths. Do not use LoadFile to load assemblies that you want to execute.&lt;br /&gt;&lt;div class="Code" id="divAssemblyLoad2"&gt;&lt;br /&gt;Assembly SampleAssembly = Assembly.LoadFrom("c:\\Sample.Assembly.dll");&lt;br /&gt;Assembly SampleAssembly2 = Assembly.LoadFrom("c:\\Sample.Assembly2.dll");&lt;br /&gt;&lt;/div&gt;&lt;br /&gt;&lt;strong&gt;LoadFile does not load files into the LoadFrom context&lt;/strong&gt;, and does not resolve dependencies using the load path, as the LoadFrom method does. LoadFile is useful in this limited scenario because &lt;strong&gt;LoadFrom cannot be used to load assemblies that have the same identities but different paths; it will load only the first such assembly&lt;/strong&gt;.&lt;p&gt;&lt;/p&gt;&lt;br /&gt;&lt;p&gt;&lt;strong&gt;&lt;/strong&gt;&lt;/p&gt;&lt;/li&gt;&lt;li&gt;&lt;strong&gt;How is a strongly-named assembly different from one that isn’t strongly-named?&lt;/strong&gt;&lt;br /&gt;Strongly-named assemblies are signed using a private\public key pair which helps with code verification.&lt;br /&gt;signed assemblies could be placed in thee GAC.&lt;p&gt;&lt;/p&gt;&lt;br /&gt;&lt;p&gt;&lt;strong&gt;&lt;/strong&gt;&lt;/p&gt;&lt;/li&gt;&lt;li&gt;&lt;strong&gt;Can DateTimes be null? &lt;/strong&gt;&lt;br /&gt;No. It is a Structure an object of it is place in the stack.&lt;p&gt;&lt;/p&gt;&lt;br /&gt;&lt;p&gt;&lt;strong&gt;&lt;/strong&gt;&lt;/p&gt;&lt;/li&gt;&lt;li&gt;&lt;strong&gt;What is the JIT? What is NGEN? What are limitations and benefits of each? &lt;/strong&gt;&lt;br /&gt;Reference &lt;a href="http://msdn.microsoft.com/library/default.asp?url=/library/en-us/cpguide/html/cpconjitcompilation.asp"&gt;Compiling MSIL to Native Code&lt;/a&gt;&lt;br /&gt;Just-In-Time compilation. (In .Net context) complier produces MSIL (the portable executable); at the first time the assembly is called, it is compiled into CPU specific native code by the .NET JIT compiler. The benefit: portable executable – ‘write once, run everywhere’; JIT compiles the code and stores result native code in memory at initial call and subsequent calls is accessing in-memory native code hence it is relatively efficient.&lt;br /&gt;&lt;br /&gt;&lt;a href="http://msdn.microsoft.com/msdnmag/issues/05/04/NGen/default.aspx"&gt;NGEN&lt;/a&gt; Pre-compilation, or pre-JITing, is the creation of native code from MSIL on the client machine, but instead of being generated at run time it is done as a separate isolated step. NGen is the term used generically for pre-JIT technology in the common language runtime (CLR), and specifically for the command-line utility used to create and store the native code. The native code produced by NGen is stored in true Win32® PE files which are called "native images" or "NGen images" which are in turn stored in the "native image cache" or "NGen cache."&lt;br /&gt;When creating native images, NGen simply loads the JIT compiler and invokes it to create native code for the assembly, which is then persisted into the native image and stored in the native image cache.&lt;br /&gt;NGEN is recommended as the last step during installation process, hence the name (native) install-time code generation?&lt;br /&gt;Note: &lt;a href="http://blogs.msdn.com/jasonz/archive/2003/09/24/53574.aspx"&gt;Consideration on using NGen&lt;/a&gt;: &lt;ul&gt;&lt;li&gt;NGen is important to getting faster startup through better page sharing and working set reduction&lt;/li&gt;&lt;br /&gt;&lt;li&gt;NGen is primarily interesting for client scenarios which need the faster startup to be responsive&lt;/li&gt;&lt;br /&gt;&lt;li&gt;NGen is not recommend for Asp.Net because the assemblies NGen produces cannot be shared between App Domains&lt;/li&gt;&lt;br /&gt;&lt;li&gt;NGen for V1.0 and V1.1 was primarily designed for the CLR, and while it can be used for shared libraries and client apps:&lt;br /&gt;Always measure to make sure it is a win for your application&lt;br /&gt;Make sure your application is well behaved in the face of brittleness and servicing&lt;br /&gt;&lt;/li&gt;&lt;/ul&gt;&lt;p&gt;&lt;/p&gt;&lt;br /&gt;&lt;p&gt;&lt;strong&gt;&lt;/strong&gt;&lt;/p&gt;&lt;/li&gt;&lt;li&gt;&lt;strong&gt;How does the generational garbage collector in the .NET CLR manage object lifetime? What is non-deterministic finalization? &lt;/strong&gt;&lt;br /&gt;CLR GC (Garbage Collection/Garbage Collector depends of the context) makes following assumptions:&lt;br /&gt;The newer an object is, the shorter its lifetime will be.&lt;br /&gt;The older an object is, the longer its lifetime will be.&lt;br /&gt;Collecting a portion of the heap is faster than collecting the whole heap.&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;Generation memory threshold&lt;/strong&gt;&lt;br /&gt;There are three (0, 1, 2) generations defined by CLR. When CLR initializes, it selects a memory threshold for each generation, say 256 Kb for g0, 2 Mb for g1 and 10 Mb for g2. GC self-tunes these thresholds to give an optimal GC frequency-process time.&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;Generation Promotion&lt;/strong&gt;&lt;br /&gt;All objects are initially put into g0. When threshold reached, GC starts compact the garbage objects. Survival objects are promoted into g1. GC won’t compact g1 until its threshold is reached. Vice versa, objects survive g1 GC are promoted into g2. When GC compacts an older generation, it also compacts younger generation(s).&lt;br /&gt;&lt;br /&gt;A Finalizable type implements &lt;span style="font-family:courier new;"&gt;Finalize&lt;/span&gt; method. GC calls this Finalize method to release the memory taken by the object. At least 2 GC processes are required to clear up finalizable objects. However, GC works on a separate thread and only starts when a generation threshold is full, there is no guarantee when Finalize will be called. This is the &lt;strong&gt;Non deterministic finalization&lt;/strong&gt;.&lt;br /&gt;&lt;br /&gt;Finalizable types should always implement &lt;em&gt;Dispose Pattern&lt;/em&gt; to allow GC &lt;strong&gt;deterministically &lt;/strong&gt;disposes it.&lt;br /&gt;&lt;p&gt;&lt;/p&gt;&lt;p&gt;&lt;strong&gt;&lt;/strong&gt;&lt;/p&gt;&lt;/li&gt;&lt;li&gt;&lt;strong&gt;What is the difference between &lt;span style="font-family:courier new;"&gt;Finalize()&lt;/span&gt; and &lt;span style="font-family:courier new;"&gt;Dispose()?&lt;/span&gt; &lt;/strong&gt;&lt;br /&gt;Finalize is non public and only called by GC. Dispose is public and called by the user of the class. Call to Dispose to cleanup an resource triggers the Finalize being called by GC later (if Finalize is implemented).&lt;br /&gt;&lt;p&gt;&lt;/p&gt;&lt;br /&gt;&lt;p&gt;&lt;strong&gt;&lt;/strong&gt;&lt;/p&gt;&lt;/li&gt;&lt;li&gt;&lt;strong&gt;How is the using() pattern useful? What is IDisposable? How does it support deterministic finalization? &lt;/strong&gt;&lt;br /&gt;We use &lt;span style="font-family:courier new;"&gt;using(…){}&lt;/span&gt; on Disposable resource such like &lt;span style="font-family:courier new;"&gt;FileStream&lt;/span&gt;. This pattern gives a visual block of the scope that a resource will be available to use and enforce the Dispose by the close brace.&lt;br /&gt;&lt;br /&gt;IDisposable, an Interface defines Dispose() method. It should be implemented by all objects, resources that need Finalization in a deterministic way. Richter suggests a very useful Dispose Pattern in his book.&lt;br /&gt;&lt;div id="divfinialize1" class="code"&gt;&lt;br /&gt;using System;&lt;br /&gt;/// &lt;summary&gt;implemeting the IDisposable interface for Dispose Pattern &lt;/summary&gt;&lt;br /&gt;public sealed class OSHandle : IDisposable{&lt;br /&gt;&lt;br /&gt;/// &lt;summary&gt;holds the Win32 handle of the unmanaged resource&lt;/summary&gt;&lt;br /&gt;private IntPtr _handle;&lt;br /&gt;&lt;br /&gt;public OSHandle(IntPtr handle){&lt;br /&gt; this._handle = handle;&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;/// &lt;summary&gt;&lt;br /&gt;/// when garbage collected, this Finalize method is called to close the&lt;br /&gt;/// unmanaged resource's handle&lt;br /&gt;/// &lt;/summary&gt;&lt;br /&gt;~OSHandle(){&lt;br /&gt; Dispose(false);&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;/// &lt;summary&gt;&lt;br /&gt;/// this public method can be called to deterministically close the unmanaged resource's handle&lt;br /&gt;/// &lt;/summary&gt;&lt;br /&gt;public void Dispose(){&lt;br /&gt; //because the object is explicitly cleaned up, stop the garbage collector from calling the&lt;br /&gt; //finalize method when this is running&lt;br /&gt; GC.SuppressFinalize(this);&lt;br /&gt; Dispose(true);&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;/// &lt;summary&gt;&lt;br /&gt;/// this public method can be called to deterministically close the unmanaged resource's handle&lt;br /&gt;/// &lt;/summary&gt;&lt;br /&gt;public void Close(){&lt;br /&gt; Dispose();&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;/// &lt;summary&gt;&lt;br /&gt;/// this method is called by Finalize, Dispose and Close to do the actual cleanup&lt;br /&gt;/// OSHandle is made 'sealed' and this method is 'private'to protect it from be called -&lt;br /&gt;/// the derived class need to implement their own cleanup then call this one.&lt;br /&gt;/// If OSHandle cannot be 'sealed' this method need to be virtual protected&lt;br /&gt;/// &lt;/summary&gt;&lt;br /&gt;/// &lt;/div&gt;&lt;/li&gt;&lt;param name="disposing"&gt;&lt;br /&gt;private void Dispose(bool disposing){&lt;br /&gt; //Synchronize threads calling Dispose/Close simutaneously&lt;br /&gt; if (disposing){&lt;br /&gt;  //the object is being explicitly disposed of/closed, not finalized. It is therefore&lt;br /&gt;  //safe for code here to access fields that reference other objects because the Finalize&lt;br /&gt;  //method of these ther objects hasn't yet been called&lt;br /&gt;&lt;br /&gt;  //For our sample OSHandle class, we have nothing to do here&lt;br /&gt; }&lt;br /&gt;&lt;br /&gt; // The object is being disposed of/closed or finalized&lt;br /&gt; if (IsValid){&lt;br /&gt;  // close the unmanaged resource&lt;br /&gt;  CloseHandle(this._handle);&lt;br /&gt;&lt;br /&gt;  // set the handle to some sentinel value. This prcaution prevents the possiblity of&lt;br /&gt;  // calling CloseHandle twice&lt;br /&gt;  this._handle = InvalidHandle;&lt;br /&gt; }&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;//Make this property return an invalid value for whatever unmanaged resource you are using&lt;br /&gt;public IntPtr InvalidHandle {get {return IntPtr.Zero; }}&lt;br /&gt;&lt;br /&gt;//Public method to return the wrapped handle&lt;br /&gt;public IntPtr ToHandle () {return this._handle ; }&lt;br /&gt;&lt;br /&gt;//public implicit cast operator returns the wrapped handle&lt;br /&gt;public static implicit operator IntPtr(OSHandle osHandle){&lt;br /&gt; return osHandle.ToHandle();&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;public bool IsValid {get {return (this._handle != InvalidHandle);}}&lt;br /&gt;public bool IsInvalid {get {return !IsValid;}}&lt;br /&gt;&lt;br /&gt;//private method called to free the unmanaged resource&lt;br /&gt;[System.Runtime.InteropServices.DllImport("Kernel32")]&lt;br /&gt;private extern static bool CloseHandle(IntPtr handle);&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;Pointer: Chapter 19 of Jeffery Richter’s Book &lt;a href="http://www.amazon.co.uk/exec/obidos/ASIN/0735614229/httifotnet-21"&gt;Applied Microsoft .NET Framework Programming&lt;/a&gt;&lt;p&gt;&lt;/p&gt;&lt;br /&gt;&lt;p&gt;&lt;strong&gt;&lt;/strong&gt;&lt;/p&gt;&lt;li&gt;&lt;strong&gt;What does this useful command line do? tasklist /m "mscor*"&lt;/strong&gt;&lt;br /&gt;&lt;div class="Code" id="divTaskList1"&gt;TASKLIST [/S system [/U username [/P [password]]]] [/M [module] | /SVC | /V] [/FI filter] [/FO format] [/NH]&lt;/div&gt;&lt;br /&gt;Description: This tool displays a list of currently running processes on either a local or remote machine.&lt;p&gt;&lt;/p&gt;&lt;br /&gt;&lt;p&gt;&lt;strong&gt;&lt;/strong&gt;&lt;/p&gt;&lt;/li&gt;&lt;li&gt;&lt;strong&gt;What is the difference between in-proc and out-of-proc? What technology enables out-of-proc communication in .NET?&lt;/strong&gt;&lt;br /&gt;Procedure call in out-of-proc requires object sterilization/marshalling. .Net Remoting enables out-of-proc communication in .NET. &lt;p&gt;&lt;/p&gt;&lt;br /&gt;&lt;p&gt;&lt;strong&gt;&lt;/strong&gt;&lt;/p&gt;&lt;/li&gt;&lt;li&gt;&lt;strong&gt;When you’re running a component within ASP.NET, what process is it running within on Windows XP? Windows 2000? Windows 2003?&lt;/strong&gt;&lt;br /&gt;In Windows XP and Windows 2000 (IIS5), ASP.NET is running in ASPnet_wp.exe worker process. In Windows 2003 (IIS6), ASP.NET is running in W3WP.exe worker process.&lt;br /&gt;P.S. Worker Process is the Application(s) pool that web application is assigned to.&lt;br /&gt;&lt;p&gt;&lt;/p&gt;&lt;a href="http://www.amazon.co.uk/exec/obidos/ASIN/0735614229/httifotnet-21"&gt;&lt;/a&gt;&lt;/li&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-111758248690422935?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='related' href='http://www.hanselman.com/blog/WhatGreatNETDevelopersOughtToKnowMoreNETInterviewQuestions.aspx' title='What Great .NET Developers Ought To Know (Part Two Mid-Level .NET Developer)'/><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/111758248690422935/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=111758248690422935' title='1 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/111758248690422935'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/111758248690422935'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2005/06/what-great-net-developers-ought-to.html' title='What Great .NET Developers Ought To Know (Part Two Mid-Level .NET Developer)'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><thr:total>1</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-111683671949006878</id><published>2005-05-23T09:11:00.000+01:00</published><updated>2006-11-01T12:22:58.047Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='asp.net'/><title type='text'>What Great .NET Developers Ought To Know (Part one Everyone who writes code)</title><content type='html'>&lt;p&gt;Scott Hanselman's - &lt;a href="http://www.hanselman.com/blog/WhatGreatNETDevelopersOughtToKnowMoreNETInterviewQuestions.aspx"&gt;What Great .NET Developers Ought To Know&lt;/a&gt; is by far the most interesting and challenging .NET interview questions I have seen so far.&lt;br /&gt;Here is my trial.&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;Part one Everyone who writes code &lt;/strong&gt;&lt;br /&gt;&lt;br /&gt;&lt;/p&gt;&lt;strong&gt;&lt;/strong&gt;&lt;li&gt;&lt;strong&gt;Process, AppDomain and Thread (change the question from ‘Describe the difference between a Thread and a Process?)&lt;/strong&gt;&lt;br /&gt;&lt;br /&gt;A &lt;strong&gt;&lt;em&gt;process&lt;/em&gt;&lt;/strong&gt; is the smallest unit of isolation available on the Windows operating system before MS .NET era. A process is a container and boundary. A process contains the executable code and data of a program inside memory it has reserved from the operating system. Erroneous code inside of a process cannot corrupt areas outside of the current process.&lt;br /&gt;&lt;br /&gt;A &lt;strong&gt;&lt;em&gt;thread&lt;/em&gt;&lt;/strong&gt; &lt;em&gt;(of execution)&lt;/em&gt; is a series of instructions and a call stack that operate independently of the other threads in a process. A process contains at least one thread executing instructions. For example, in a windows form application there will at least one and the main thread - UI thread. In most cases, there will be multiple threads running asynchronously.&lt;br /&gt;&lt;br /&gt;.NET runtime introduces a finer unit over process - &lt;strong&gt;&lt;em&gt;AppDomain&lt;/em&gt;&lt;/strong&gt;. An AppDomain belongs to only one single process, but single process can hold multiple AppDomains. Like a process, the AppDomain is both a container and a boundary. The .NET runtime uses an AppDomain as a container for a set of assemblies (code) and data, just like the operating system uses a process as a container for code and data. As the operating system uses a process to isolate misbehaving code, the .NET runtime uses an AppDomain to isolate code inside of a secure boundary.&lt;br /&gt;&lt;br /&gt;By default, an assembly is loaded once per AppDomain. Considering case: A process contains multiple AppDomain. Each AppDomain loads an assembly &lt;span style="font-family:courier new;"&gt;myCommon.dll&lt;/span&gt;. The static members and data of &lt;span style="font-family:courier new;"&gt;myCommon.dll&lt;/span&gt; are isolated by the AppDomain boundary. They are not shared at process level. &lt;p&gt;&lt;/p&gt;&lt;p&gt;Some assemblies are expected to be used by several AppDomains, e.g. &lt;span style="font-family:courier new;"&gt;MSCorLib.dll&lt;/span&gt;. They are AppDomain neutral and are loaded to a special loader heap managed by CLR. They cannot be unloaded until the process terminates.&lt;br /&gt;&lt;br /&gt;Code in one AppDomain can communicate with types and objects contained in another AppDomain by .NET mechanism such like Remoting. When a thread in one AppDomain calls a method in another AppDomain, the thread transitions between the two AppDomain – the call is synchronous. At any one given time, a thread is considered to be in just one AppDomain.&lt;br /&gt;&lt;br /&gt;An AppDomain is relatively cheap to create (compared to a process), and has relatively less overhead to maintain than a process.&lt;br /&gt;&lt;br /&gt;&lt;u&gt;&lt;strong&gt;Pointers&lt;/strong&gt;: IIS worker process, Thread Pool,&lt;br /&gt;&lt;/u&gt;&lt;a href="http://odetocode.com/Articles/305.aspx"&gt;http://odetocode.com/Articles/305.aspx&lt;/a&gt;&lt;br /&gt;&lt;a href="http://www.amazon.co.uk/exec/obidos/ASIN/0735614229/httifotnet-21"&gt;Applied Microsoft .NET Framework Programming&lt;/a&gt; &lt;a href="http://www.amazon.co.uk/exec/obidos/ASIN/0735617228/httifotnet-21"&gt;Designing Microsoft ASP.NET Application&lt;/a&gt;&lt;br /&gt;&lt;/p&gt;&lt;br /&gt;&lt;br /&gt;&lt;p&gt;&lt;strong&gt;&lt;/strong&gt;&lt;/p&gt;&lt;/li&gt;&lt;li&gt;&lt;strong&gt; What is a Windows Service and how does its lifecycle differ from a "standard" EXE? &lt;/strong&gt;&lt;br /&gt;Windows services run as long-running background processes. A Windows service is installed in the registry as an executable object. It is managed by the Service Control Manager (SCM). SCM is a remote procedure call (RPC) server, supports local or remote management of a service. For example, automatically start, stop services while OS starts or stop.&lt;br /&gt;&lt;br /&gt;Windows service can be specified to run in the security context of a specific user account that’s different from the logged on user or the default system account. Therefore, a Windows service can be started before a user logs on and continue to run even after the user logs off.&lt;br /&gt;&lt;br /&gt;As Windows services running as background processes, all events or dialogs raises are not visible to users. They are all written to system EventLog.&lt;br /&gt;&lt;br /&gt;A ‘standard’ exe is executed by current logged on user and by default runs in the current user’s security context. It runs at the ‘foreground’ as application. It interacts with user directly. It stops when the execution completed or is stopped by the user or when user logs off.&lt;br /&gt;&lt;p&gt;&lt;/p&gt;&lt;br /&gt;&lt;br /&gt;&lt;p&gt;&lt;strong&gt;&lt;/strong&gt;&lt;/p&gt;&lt;/li&gt;&lt;li&gt;&lt;strong&gt;What is the maximum amount of memory any single process on Windows can address? Is this different than the maximum virtual memory for the system? How would this affect a system design?&lt;/strong&gt;&lt;br /&gt;&lt;br /&gt;A single process on X86 windows can normally address 2GB memory (the virtual address space, regardless of the amount of physical memory that is actually available). Although &lt;a href="http://support.microsoft.com/default.aspx?scid=kb;EN-US;833721"&gt;Windows 2003 enable 3GB virtual address space&lt;/a&gt;. The maximum virtual memory for a 32-bit system is 4GB, 2GB of it is allocated to Kernel.&lt;br /&gt;This affects system design when designing for memory intensive applications such as databases, enterprise applications etc...&lt;br /&gt;&lt;strong&gt;Pointers&lt;/strong&gt;: &lt;a href="http://msdn.microsoft.com/library/default.asp?url=/library/en-us/dngenlib/html/msdn_virtmm.asp"&gt;Managing Virtual Memory in Win32&lt;/a&gt;&lt;br /&gt;&lt;p&gt;&lt;/p&gt;&lt;br /&gt;&lt;br /&gt;&lt;p&gt;&lt;strong&gt;&lt;/strong&gt;&lt;/p&gt;&lt;/li&gt;&lt;li&gt;&lt;strong&gt;What is the difference between an EXE and a DLL?&lt;/strong&gt;&lt;br /&gt;&lt;br /&gt;DLL, or Dynamic Link Library (binary files) provides a library of functions to application (EXE) at run time. DLLs are linked to an application when it is &lt;strong&gt;loaded and executed&lt;/strong&gt; at run time rather than when it is linked (at compilation time with the referencing application). When an application (EXE) uses a DLL, the operating system loads the DLL into memory, resolves references to functions in the DLL so that it can be called by the application, and unloads the DLL when it is no longer needed.&lt;br /&gt;&lt;br /&gt;The main difference is a DLL is in-process, meaning it runs within the callee/client process An EXE is out-of-process, meaning runs within its own process.&lt;br /&gt;&lt;u&gt;Pointers: Security context, threading model&lt;/u&gt;&lt;br /&gt;&lt;p&gt;&lt;/p&gt;&lt;br /&gt;&lt;br /&gt;&lt;p&gt;&lt;strong&gt;&lt;/strong&gt;&lt;/p&gt;&lt;/li&gt;&lt;li&gt;&lt;strong&gt;What is strong-typing versus weak-typing? Which is preferred? Why?&lt;/strong&gt;&lt;br /&gt;&lt;br /&gt;In a weakly typed language, the type of a value depends on how it is used. For example if I can pass a string to the addition operator and it will be interpreted as a number or cause an error if the contents of the string cannot be translated into a number. Similarly, I can concatenate strings and numbers or use strings as booleans, etc. And complier (if compiling required) would not found the mis-type conversion.&lt;br /&gt;&lt;br /&gt;In a strongly typed language, a value has a type and that type cannot change. What you can do to a value depends on the type of the value. Mis-type conversion will be caught by compliers. With model IDE, such like Visual Studio 2003 and add-ins like &lt;a href="http://www.jetbrains.com/resharper/"&gt;Resharper&lt;/a&gt;, the issue is reported simultaneously as typing, even before hitting ‘build’ button.&lt;br /&gt;&lt;br /&gt;The advantage of a strongly typed language is that you are forced to make the behaviour of your program explicit. If you want to add a number and a string your code must translate the string into a number to be used as an operand of the addition operator. This makes code easier to understand because there is no (or less) hidden behaviour. However, it also makes your code more verbose.&lt;br /&gt;The advantage of a weakly typed language is that you need to write less code. However, that code is harder to understand because a lot of its behaviour is hidden in implicit type conversions.&lt;br /&gt;&lt;br /&gt;(Cited from &lt;a href="http://c2.com/cgi/wiki?WeakAndStrongTyping"&gt;http://c2.com/cgi/wiki?WeakAndStrongTyping&lt;/a&gt;)&lt;br /&gt;From a more practical point of view I reckon strong-type and weak-type are mainly for the developer’s benefit on code self-documentation. Because though in weak-type language implementations, type conversion problem will only surface at run time. You certainly will unit test every corner before release it. In fact you should write your test cases before writing codes (What? Do you say you can’t do &lt;a href="http://www.amazon.co.uk/exec/obidos/ASIN/0321146530/httifotnet-21"&gt;Test Driven Development&lt;/a&gt; for scripting languages?)&lt;br /&gt;&lt;p&gt;&lt;/p&gt;&lt;br /&gt;&lt;br /&gt;&lt;p&gt;&lt;strong&gt;&lt;/strong&gt;&lt;/p&gt;&lt;/li&gt;&lt;li&gt;&lt;strong&gt;Corillian's product is a "Component Container." Name at least 3 component containers that ship now with the Windows Server Family.&lt;/strong&gt;&lt;br /&gt;&lt;br /&gt;System.Web.UI.Page, System.Windows.Forms.Form and System.ComponentModel.Container&lt;br /&gt;The essence of component development is not to build what you can buy. Buy a rich text web control from the market for $99 instead of design and implement one from scratch. Snapping together pre-tested components are faster, cheaper and probably more reliable than coding everything for yourself.&lt;br /&gt;What is a '.NET component'? Arguably, almost any .NET class file is a component, in that it can easily be compiled to a DLL, it benefits from .NET versioning, and it can be reused. If you narrow the definition to components that are 'designable', in other words you can drop instances onto a Visual Studio .NET design surface and set their properties or create event handlers visually, then you need a class that directly or indirectly implements IComponent. Designable objects do not necessarily have a user interface. Those that do are controls as well as components, and inherit from System.Windows.Forms.Control or System.Web.UI.Control.&lt;br /&gt;The existence of components also implies the existence of containers, which again may be visual or non-visual. In the .NET Framework both ASP.NET Web Forms and rich client Windows Forms are visual component containers. The container plays an important role in component management. In particular, all containers implement IDisposable, which means they have a Dispose method for releasing unmanaged resources such as window handles or open files. In their Dispose method, containers must also call Dispose on all the components they host.&lt;br /&gt;&lt;p&gt;&lt;strong&gt;&lt;/strong&gt;&lt;/p&gt;&lt;/li&gt;&lt;li&gt;&lt;strong&gt;What is a PID? How is it useful when troubleshooting a system?&lt;/strong&gt;&lt;br /&gt;&lt;br /&gt;PID stands for Process Identifier, a uniquely assigned integer that identifies a process in the operating system. In any system, applications use PID to identify the process uniquely. Also, it is used in diagnosing the problems with the process in Multi-Tasking systems.&lt;br /&gt;&lt;p&gt;&lt;/p&gt;&lt;br /&gt;&lt;p&gt;&lt;strong&gt;&lt;/strong&gt;&lt;/p&gt;&lt;/li&gt;&lt;li&gt;&lt;strong&gt;How many processes can listen on a single TCP/IP port?&lt;/strong&gt;&lt;br /&gt;&lt;br /&gt;As many as you like? But do it this way is strange. You probably will only want one process listening to a TCP/IP port, so it can handle the data solely.&lt;br /&gt;What is the GAC? What problem does it solve?&lt;br /&gt;Global Assembly Cache. It is a machine-wide code cache. Assemblies deployed in the global assembly cache must have a strong name. GAC solves the problems of versioning, DLL hell etc. &lt;p&gt;&lt;/p&gt;&lt;/li&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-111683671949006878?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='related' href='http://www.hanselman.com/blog/WhatGreatNETDevelopersOughtToKnowMoreNETInterviewQuestions.aspx' title='What Great .NET Developers Ought To Know (Part one Everyone who writes code)'/><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/111683671949006878/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=111683671949006878' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/111683671949006878'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/111683671949006878'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2005/05/what-great-net-developers-ought-to.html' title='What Great .NET Developers Ought To Know (Part one Everyone who writes code)'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-111637091088123594</id><published>2005-05-18T00:00:00.000+01:00</published><updated>2006-11-01T12:23:32.392Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='win server'/><title type='text'>BizTalk Server 2004 Setup/Architecture</title><content type='html'>Stand-Alone Instance(s)&lt;br /&gt;http://geekswithblogs.net/mhamilton/articles/37527.aspx&lt;br /&gt;&lt;br /&gt;Multiple Computers (Domain)&lt;br /&gt;http://msdn.microsoft.com/library/default.asp?url=/library/en-us/deploying/htm/ebiz_depl_config_dibn.asp&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-111637091088123594?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/111637091088123594/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=111637091088123594' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/111637091088123594'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/111637091088123594'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2005/05/biztalk-server-2004-setuparchitecture.html' title='BizTalk Server 2004 Setup/Architecture'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-111558877517727304</id><published>2005-05-08T22:16:00.000+01:00</published><updated>2006-11-01T12:26:44.905Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='win server'/><title type='text'>Build a Windows Server Farm with Virtual Server 2005 (Observation)</title><content type='html'>&lt;p&gt;Got a Dell &lt;a href="http://www1.us.dell.com/content/topics/global.aspx/power/en/ps4q99_aten?c=us&amp;cs=555&amp;amp;l=en&amp;s=biz"&gt;PowerEdge 6350 Server&lt;/a&gt; with dual CPU (550 MHz/512), 4Gb Ram from eBay recently. The idea is to create a development/testing environment that simulates an online transaction environment using this server machine. I install Windows 20003 server (W2K3) on the physical machine, then use Microsoft Virtual Server 2005 to host a number of guest server OS.&lt;br /&gt;&lt;br /&gt;A Windows 2000 server (W2K) is acted as domain controller (DC). I use a spare laptop for this to avoid the chicken and egg problem (I will come to &lt;a href="http://beta.blogger.com/post-edit.g?blogID=6082242&amp;amp;postID=111558877517727304#chickenEgg"&gt;the point&lt;/a&gt; later). I found Daniel Petri has a very useful &lt;a href="http://www.petri.co.il/create_a_new_dns_server_for_ad.htm"&gt;step by step guide&lt;/a&gt; on how to configure domain controller.&lt;br /&gt;&lt;br /&gt;All goes well until I accidentally tripped the charger and knocked the laptop to the ground. Fortunately my boss ‘lent’ me another laptop (PII 550MHz, 192Mb RAM). So I could reinstall the DC and have host and guest OS removed and rejoin the domain.&lt;br /&gt;&lt;br /&gt;In retrospective of the entire exercise, I have following points.&lt;/p&gt;&lt;p&gt;&lt;strong&gt;1 CPU Consideration&lt;/strong&gt;&lt;br /&gt;Virtual Server 2005 masks actual hardware and simulates an IDE desktop machine with single CPU. So the using this Dell machine gains benefit by balancing guest OS processes weight across the two CPUs. A specific guest OS always runs on a single CPU.&lt;br /&gt;&lt;br /&gt;This becomes a problem if install w2k3 as a guest OS. As the hardware concerned, a single CPU emulation environment does not meet the minimum hardware requirements for W2K3. In fact, the installation process taking so long that I have to abort it.&lt;br /&gt;&lt;br /&gt;Nevertheless, having W2K3 as host OS is fine, because it can fully exploit both CPUs’ capacity. (MS Virtual Server 2005 is compatible with W2K3 only).&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;2 Virtual Hard Drive&lt;/strong&gt;&lt;br /&gt;To preserve the hard drive space, I use ‘&lt;a href="http://www.microsoft.com/technet/prodtechnol/virtualserver/2005/proddocs/vs_deploy_setup_VM_disks_hd.mspx"&gt;Differencing Virtual Hard Disk&lt;/a&gt;’. The first thing after starting a guest OS that is built on child virtual hard disk is to use Microsoft &lt;a href="http://www.microsoft.com/windows2000/downloads/tools/sysprep/default.asp"&gt;sysprep&lt;/a&gt; tool to gain a new system identity.&lt;br /&gt;&lt;br /&gt;In retrospective, I should have made the parent virtual hard disk bigger. Child disk is sized based on the size of the parent’s. So if parent disk is 3Gb, child disk is also 3Gb. The W2K OS takes about 2Gb space. After running sysprep on child disk, it’s vhd file dynamically grows to 1.2Gb – not a lot of space remained.&lt;br /&gt;&lt;br /&gt;In this situation you can attach a secondary virtual hard drive to the guest OS in question. It is just convenient to have a bigger primary drive in situations that windows installation can go into the default ‘C:\Program Files’ folder.&lt;br /&gt;&lt;strong&gt;&lt;br /&gt;3 Network Interface Card (NICs) and connections&lt;/strong&gt;&lt;br /&gt;The Dell server comes with two NICs and two onboard NICs (not used at the moment). To maximum performance throughput they are configured as:&lt;br /&gt;&lt;br /&gt;Card 1/Connection 1 is dedicated to the guest virtual network. So all guest OS will use this NIC to participate the domain network. On host OS, all network protocols bind to this NIC removed and leave only virtual machine network services checked. On each guest OS TCP/IP protocols is bound and assigned unique static IP addresses.&lt;br /&gt;&lt;br /&gt;Card 2/Connection 2 is designed for handling network traffic of the host server. It TCP/IP protocols enabled but virtual machine network services unbind.&lt;br /&gt;&lt;br /&gt;Connection 3 is a loop-back adapter for handling file sharing and other network traffic between guest and host systems without having them travel externally.&lt;br /&gt;&lt;br /&gt;Connection 1 and 3 needed to be added to the virtual server to create two virtual networks (&lt;a href="http://beta.blogger.com/post-edit.g?blogID=6082242&amp;postID=111558877517727304#Note1"&gt;Note 1&lt;/a&gt;). Also check &lt;a href="http://beta.blogger.com/post-edit.g?blogID=6082242&amp;amp;postID=111558877517727304#Note2"&gt;Note 2&lt;/a&gt; on how to configure loop-back adapter for file sharing, or Host-Guest network traffic.&lt;br /&gt;&lt;br /&gt;Virtual server emulates these NIC/connections in the guest systems. In my configuration, they all called ‘Intel 21140 Based PCI Fast Ethernet Adapter’. Virtual server generates a dynamic MAC address for each NIC on each guest OS (&lt;a href="http://beta.blogger.com/post-edit.g?blogID=6082242&amp;postID=111558877517727304#Note3"&gt;Note 3&lt;/a&gt;). This is of course different from the physical MAC address.&lt;br /&gt;&lt;br /&gt;It is very easy to confuse on which NIC is for what purpose. So I would suggest make a note on the dynamic MAC addresses before configuring the TCP/IP protocols in the guest OS.&lt;br /&gt;&lt;br /&gt;If more NICs are added via Virtual Server Administration website, on guest OS you can run hardware scan/update to pick them up like you will normally do on real machine.&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;4 Domain Controllers&lt;/strong&gt;&lt;br /&gt;There are a few options available when comes to where to place the domain controller in this garage network. Microsoft’s &lt;a href="http://www.microsoft.com/downloads/details.aspx?FamilyId=64DB845D-F7A3-4209-8ED2-E261A117FC6B&amp;amp;displaylang=en"&gt;Running a Domain Controller in Virtual Server 2005&lt;/a&gt; gives a step-by-step guide on network planning for virtual servers environment with following scenario.&lt;br /&gt;1) Domain controller on host OS, application servers on guest OS.&lt;br /&gt;2) Domain controller on guest OS, application servers on host OS.&lt;br /&gt;3) Both domain controller and application servers are on guest OS.&lt;br /&gt;&lt;br /&gt;The article gives credits to solution 3. It creates a pure virtual network. It has a clear defined network boundary with performance consideration.&lt;br /&gt;&lt;br /&gt;In my opinion, solution 1 degrades the virtual server performance. Virtual server required IIS 6 to be running for administration via a web site. Having domain controller and IIS running on same server degrades IIS.&lt;br /&gt;&lt;br /&gt;Solution 2 has application servers on host OS. Excuse me, but having guest OS running application server is you want originally, isn’t it?&lt;br /&gt;&lt;br /&gt;There is also a &lt;a name="chickenEgg"&gt;chicken and Egg&lt;/a&gt; problem. Solution 2 and 3 requires to have domain controller installed on a guest OS. This is not a very option for my situation. The Dell server is placed in the conservatory and accessed via remote desktop (terminal services in admin mode) connection from the study room over a wireless connection.&lt;br /&gt;&lt;br /&gt;If I install the DC in a virtual server, I must stay in the conservatory and wait for the host to boot-up, launch the guest OS (can set it to launch automatically though). Host server cannot participate in this domain. Which may cause problems in the future, for instance, file sharing issue when required to configure more virtual machines; or if the virtual network requires a W2K3 server – such like Microsoft BizTalk Business Activity Service Monitoring. BAS requires SharePoint services. And SharePoint can only deployment on W2K3.&lt;br /&gt;&lt;br /&gt;So I decide to configure an old laptop as a DC and reducing a guest OS from the virtual server. This helps to off-load some CPU and memory load from the host as well. It looked like this:&lt;/p&gt;&lt;p&gt;&lt;img src="http://www.i-fotos.net/pub/Jblog/Network_Diagram_gif_3.gif" /&gt;&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;5 Virtual Server Administration Website user authentication&lt;/strong&gt;&lt;br /&gt;The issue discussed here need to re-apply if the host/guest OS have their domain membership changed (&lt;a href="http://beta.blogger.com/post-edit.g?blogID=6082242&amp;postID=111558877517727304#Note4"&gt;Note 4&lt;/a&gt;).&lt;br /&gt;&lt;br /&gt;On access the VS admin site, it is likely you will be challenged by an Internet security pop-out window or the website will prompt you for valid credentials. If you are sure the username and password are correct and it is not accepted, it is likely that the user is not grant access to the admin website.&lt;br /&gt;&lt;br /&gt;There are two things here. First, we should allow IE send the NT credentials automatically. Then we need to grant user access to the virtual server admin site.&lt;br /&gt;&lt;br /&gt;1) Add the admin site to Local Intranet category via Internet Options Security tab. Then click the ‘Custom Level…’ button on the security tab. Security Setting window pops out. Scroll to the bottom of the settings, there is an option – ‘User Authentication Logon’. Make sure it is ‘Automatically logon only in Intranet Zone’ or ‘automatically logon with current username and password’ selected.&lt;br /&gt;&lt;br /&gt;2) Browse to the admin site, logon as a local administrator. Click on Virtual Server Server Properties on left navigation column, then click on ‘Virtual Server Security’. Then add domain users to the list.&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;6 Terminal Services and Remote Access&lt;br /&gt;&lt;/strong&gt;Normally you will access guest OS via remote desktop connection. This is supported by terminal services on W2K3 and W2K server (&lt;a href="http://beta.blogger.com/post-edit.g?blogID=6082242&amp;amp;postID=111558877517727304#Note5"&gt;Note 5&lt;/a&gt;).&lt;br /&gt;Again, the issue discussed here need to re-apply if the host/guest OS have their domain membership changed.&lt;br /&gt;&lt;br /&gt;The problem occurs when you remote access guest OS with a non-administrator NT account and on successful login it display this error message: ‘You Do Not Have Access to Logon to This Session’ and you are thrown out.&lt;br /&gt;&lt;br /&gt;To get over this problem, you need to grant remote access permission to the users/groups via Terminal Services Configuration on each guest OS.&lt;br /&gt;&lt;br /&gt;For detail see Microsoft knowledge base article &lt;a href="http://support.microsoft.com/kb/224395/EN-US/"&gt;224395&lt;/a&gt;.&lt;br /&gt;&lt;br /&gt;&lt;/p&gt;&lt;li&gt;&lt;a name="Note1"&gt;&lt;strong&gt;Note 1&lt;/strong&gt;&lt;/a&gt;   This is done via virtual server administration website). There should an existing one: ‘Internal Virtual Network’ which deploys DHCP and enable virtual machines to see each other.&lt;br /&gt;&lt;/li&gt;&lt;li&gt;&lt;a name="Note2"&gt;&lt;strong&gt;Note 2&lt;/strong&gt;&lt;/a&gt; Loop-back adapter configuration (from Virtual Server 2005 accompanied guide vs.chm)&lt;br /&gt;&lt;br /&gt;&lt;blockquote&gt;&lt;span style="font-size:85%;"&gt;1. On the host operating system, open Network Connections, right-click the local&lt;br /&gt;area connection for Microsoft Loopback Adapter, and then select Properties.&lt;br /&gt;2. In the Microsoft Loopback Adapter Properties dialog box, verify that the&lt;br /&gt;Virtual Machine Network services check box is selected.&lt;br /&gt;3. Click Internet&lt;br /&gt;Protocol (TCP/IP), and then click Properties.&lt;br /&gt;4. On the General tab, click&lt;br /&gt;Use the following IP address, and then type the IP address and subnet mask (such&lt;br /&gt;as 192.168.1.1 and 255.255.255.0).&lt;br /&gt;&lt;br /&gt;Important&lt;br /&gt;You can use any&lt;br /&gt;Transmission Control Protocol/Internet Protocol (TCP/IP) address, but it is best&lt;br /&gt;to choose one from a reserved range of non-routable TCP/IP addresses. For&lt;br /&gt;example, TCP/IP addresses of the form 192.168.x.y, where x is a value from 0&lt;br /&gt;through 255 and y is a value from 1 through 254, are non-routable. The value you&lt;br /&gt;choose for x must be the same on the host operating system and each guest&lt;br /&gt;operating system that is to be part of this virtual network. If your primary&lt;br /&gt;Ethernet connection uses one of these non-routable addresses, you must choose a&lt;br /&gt;different value for x to assign to Microsoft Loopback Adapter.&lt;br /&gt;5. Click OK,&lt;br /&gt;and then click Close.&lt;br /&gt;Notes&lt;br /&gt;· To perform this procedure, you must be an&lt;br /&gt;administrator or a member of the Administrators group.&lt;br /&gt;· To set up multiple&lt;br /&gt;network connections using Microsoft Loopback Adapter, use different subnets.&lt;br /&gt;· Do not set a value for Default gateway.&lt;/span&gt;&lt;br /&gt;&lt;/blockquote&gt;&lt;/li&gt;&lt;li&gt;&lt;a name="Note3"&gt;&lt;strong&gt;Note 3&lt;/strong&gt;&lt;/a&gt; The dynamic MAC addresses for a guest OS can be found from its configuration page on the Virtual Server Administration website, then follow the link ‘Network Adapters’.&lt;br /&gt;&lt;/li&gt;&lt;li&gt;&lt;a name="Note4"&gt;&lt;strong&gt;Note 4&lt;/strong&gt;&lt;/a&gt;   In my case, the domain controller was unrecoverable and has to be reinstalled and configured on a replacement laptop. Though I use the same domain name, active directory is essentially different from the previous one. So all domain members need to drop their existing memberships and rejoin the domain.&lt;br /&gt;&lt;/li&gt;&lt;li&gt;&lt;a name="Note5"&gt;&lt;strong&gt;Note 5&lt;/strong&gt;&lt;/a&gt;   You need to obtain license if use terminal service in application mode. For use it in administration mode you don’t need license and can have up to two concurrent connections.&lt;br /&gt;&lt;/li&gt;&lt;p&gt;&lt;/p&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-111558877517727304?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/111558877517727304/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=111558877517727304' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/111558877517727304'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/111558877517727304'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2005/05/build-windows-server-farm-with-virtual.html' title='Build a Windows Server Farm with Virtual Server 2005 (Observation)'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-111537122529453000</id><published>2005-05-06T09:39:00.000+01:00</published><updated>2006-11-01T12:26:51.321Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='win server'/><title type='text'>Forgot the Administrator password</title><content type='html'>Shit can happen and it will always happen on an unexpected time. Such like forget your administrator password (what could be worst after a two’s holiday?)&lt;br /&gt;&lt;br /&gt;Daniel Petri introduces a useful tick on &lt;a href="http://www.petri.co.il/forgot_administrator_password_alternate_logon_trick.htm"&gt;reset the LOCAL Administrator password&lt;/a&gt;. The trick is to force launch a command line console window into the misfortune OS and reset the admin password before hit the ‘CTRL+ALT+DEL’. To do so, you need to fool the start-up process to use CMD.exe instead of logon.scr as the screen saver.&lt;br /&gt;&lt;br /&gt;This is not to be confused with &lt;a href="http://www.petri.co.il/reset_domain_admin_password_in_windows_2000_ad.htm"&gt;reset DOMAIN Administrator password&lt;/a&gt;. It follows a similar method to force into the system and therefore reset the password on the domain controller. The addition is that you need to create an &lt;a href="http://www.petri.co.il/forgot_administrator_password.htm#1"&gt;Offline NT Password &amp;amp; Registry Editor boot disk&lt;/a&gt; so that you can local(offline) login to the domain controller machine.&lt;br /&gt;&lt;br /&gt;I haven’t tried neither of them yet. Who knows, I am the admin of my home web farm and I may go for a cross-land tour.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-111537122529453000?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='related' href='http://www.petri.co.il/forgot_administrator_password_alternate_logon_trick.htm' title='Forgot the Administrator password'/><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/111537122529453000/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=111537122529453000' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/111537122529453000'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/111537122529453000'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2005/05/forgot-administrator-password.html' title='Forgot the Administrator password'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-111470255818993965</id><published>2005-04-28T16:31:00.000+01:00</published><updated>2006-11-01T12:26:56.893Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='SOA'/><title type='text'>Aspect Oriented Programming in .NET</title><content type='html'>Some (relatively) easy reading: &lt;a href="http://www.theserverside.net/articles/showarticle.tss?id=AspectOrientingNET"&gt;Aspect Orienting .NET Components&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;a href="http://www.c-sharpcorner.com/Code/2002/Nov/aop.asp"&gt;&lt;/a&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-111470255818993965?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/111470255818993965/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=111470255818993965' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/111470255818993965'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/111470255818993965'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2005/04/aspect-oriented-programming-in-net.html' title='Aspect Oriented Programming in .NET'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-111088875427982537</id><published>2005-03-15T12:12:00.000Z</published><updated>2006-11-01T12:27:07.113Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='SOA'/><title type='text'>A Service-Oriented Architecture for Enabling Centralized Authentication Across WebLogic Domains</title><content type='html'>This paper:&lt;br /&gt;&lt;a href="http://dev2dev.bea.com/technologies/soa/articles/ssosaml.jsp"&gt;A Service-Oriented Architecture for Enabling Centralized Authentication Across WebLogic Domains&lt;/a&gt; contains a few diagrams very clearly describe SOA and SAML together that provides a centralised security gateway. Example is given in WebLogic Web Server, but same principles apply to any web server. Likewise, LDAP is used to search user credentials but can use any mechanism, e.g. an account database for e-Commerce application.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-111088875427982537?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='related' href='http://dev2dev.bea.com/technologies/soa/articles/ssosaml.jsp' title='A Service-Oriented Architecture for Enabling Centralized Authentication Across WebLogic Domains'/><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/111088875427982537/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=111088875427982537' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/111088875427982537'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/111088875427982537'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2005/03/service-oriented-architecture-for.html' title='A Service-Oriented Architecture for Enabling Centralized Authentication Across WebLogic Domains'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-111018981336655014</id><published>2005-03-07T10:03:00.000Z</published><updated>2006-11-01T12:27:23.115Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='web service'/><title type='text'>London Stock Exchange Retail Service Provider Gateway - Programming with WSE</title><content type='html'>LSE RSP Gateway (London Stock Exchange Retail Service Provider Gateway) is a London Stock Exchange service providing a central facility for routing quote and execution messages between private client brokers and Retail Service Providers.&lt;br /&gt;&lt;br /&gt;Based on the public information available on: &lt;a href="http://www.londonstockexchange.com/NR/rdonlyres/0228507E-1FB8-485A-9A1E-6FCEFE47EA0B/0/RSPTechnicalCTGPresentation210205website.ppt"&gt;RSP Technical CTG Presentation&lt;/a&gt;, design and implement a RSP Gateway using SOAP messaging and &lt;a href="http://msdn.microsoft.com/library/default.asp?url=/library/en-us/wse/html/080decf0-d17e-4ea3-b8bc-d7e6960326a1.asp"&gt;WSE&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;What we trying to achieve by this exercise:&lt;/strong&gt;&lt;br /&gt;This exercise will likely to use knowledge you have on following domain: SOAP (synchronous/asynchronous) messaging, web services, multithread, WSE (Web Services Enhancements), windows services, instrumentation, configuration &lt;br /&gt;&lt;br /&gt;&lt;strong&gt;Draft requirement and tasks list&lt;/strong&gt;&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;Part 1 The Gateway&lt;/strong&gt;&lt;br /&gt;Task1. Implement functions listening to income requests for stock quote from brokers.&lt;br /&gt;Task2.  Implement functions reply to brokers for the stocks prices asked.&lt;br /&gt;Task3. Implement functions ‘broadcasts’ request to RSPs for quotes on a particular stock.&lt;br /&gt;Task4. Collect quotes from RSPs&lt;br /&gt;Task5. Orchestrate the workflow, business logics.&lt;br /&gt;Task6. If the gateway is not implemented as a windows service, please turn that into a windows service.&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;Part 2 The broker and RSP console&lt;/strong&gt;&lt;br /&gt;Task1. Implement a broker console program that request stocks quotes from RPS Gateway and display the stock quotes&lt;br /&gt;Task2. Implement a RSP console that reply to RSP with their best price.&lt;br /&gt;Task3. Demonstrate multiple brokers and RSP work concurrently&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;Part 3 Deal Execution&lt;/strong&gt;&lt;br /&gt;Task1 Modify the gateway so it can propagate deal requests to the RSP based on the offer. (Broker to provide information on who offers the deal so the gateway can route it to the specific RSP).&lt;br /&gt;Task2 Modify the gateway so the dealt result from RSP can be routed back to the broker.&lt;br /&gt;Task 3. Modify the broker console to handle deal request and reply.&lt;br /&gt;Task 4. Modify the RSP console to handle deal execution and reply.&lt;br /&gt;&lt;br /&gt;Hope I can find some time this week.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-111018981336655014?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/111018981336655014/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=111018981336655014' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/111018981336655014'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/111018981336655014'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2005/03/london-stock-exchange-retail-service.html' title='London Stock Exchange Retail Service Provider Gateway - Programming with WSE'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-111010532965550457</id><published>2005-03-06T10:35:00.000Z</published><updated>2006-11-01T12:27:31.487Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='SOA'/><title type='text'>Service-Oriented Architectures (SOA)</title><content type='html'>SOA is the new buzz word everyone in the architect team is talking about. The other two are SmartClient and WSE, by the way. So what is SOA? What a service-oriented application looked like? What is drive for SOA? What are the implications in terms of customer experience, operation benchmarks: reliability, availability, scalability, performance etc and software engineering: implementation process agility, data and process modelling and designed patterns.&lt;br /&gt;&lt;br /&gt;&lt;span style="font-size:85%;"&gt;After a week’s miserable, wintry days, I am sitting in my study whcih flooded with sunshine, enjoying this glorious Sunday morning. What could be an even better thing to consolidate all these? I even have my sunglasses on .The better half is tidying up the front garden. Bless her.&lt;br /&gt;&lt;/span&gt;&lt;br /&gt;&lt;strong&gt;What is SOA?&lt;/strong&gt;&lt;br /&gt;By definition from &lt;a href="http://www.microsoft.com/NET/basics_faq.aspx#service"&gt;Microsoft .NET Frequently Asked Questions&lt;/a&gt;, ‘SOA describes an information technology architecture that enables distributed computing environments with many different types of computing platforms and applications.’ SOA is not a programming language, nor a programming model, nor a Design Pattern. It is an emerged ENTERPRISE Pattern.&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;What SOA looked like?&lt;/strong&gt;&lt;br /&gt;In typical n-tier enterprise architectures, SOA abstracts middle tiers and exposes the complex business object interactions and heterogeneous backend (say composed of a DB2 database, an Oracle and a few 3rd party extranet calls) as ‘contract-services’. The result is a ‘loosely coupled, and standards based’(&lt;a href="http://www.blogger.com/"&gt;Dave Chappell Extracting Business Value from SOA &lt;/a&gt;)enterprise system.&lt;br /&gt;&lt;br /&gt;Following figures are from Chip Irek’s excellent paper &lt;a href="http://www.15seconds.com/issue/031215.htm"&gt;Realizing a Service-Oriented Architecture with .NET&lt;/a&gt; shows a sitting plan of the SOA service interface.&lt;br /&gt;&lt;br /&gt;&lt;img src="http://www.15seconds.com/graphics/issue/031217_02.gif" /&gt;&lt;br /&gt;A typical 3-tier application architecture&lt;br /&gt;&lt;br /&gt;&lt;img src="http://www.15seconds.com/graphics/issue/031217_03.gif" /&gt;&lt;br /&gt;A service-oriented application architecture&lt;br /&gt;&lt;br /&gt;Now image this is a simplified IT architecture of a bank. There are handheld devices, browser client and other smart clients the presentation box needs to support for internal and external customers. For a typical transaction of credit account, it involves customer database, product database and calls to &lt;a href="http://www.bacs.co.uk/bpsl/corporate"&gt;BACS&lt;/a&gt; (Bankers Automated Clearing System).&lt;br /&gt;&lt;br /&gt;As you can see in the second figure, the purple cloud - service interface wraps the entire transaction and exposes it as single point of contact to the caller – the presentation box. (The two cubicles in the purple cloud should be read as two unrelated requests happened to be invoked from the same client to simplify the case.)&lt;br /&gt;&lt;br /&gt;On receiving a client request, ‘services purple cloud’ orchestrates calls to discreet business objects (traditional middleware), in our case retrieving customer data, retrieving product information and issues a request for credit to BACS. The purple cloud also manages the responses, and finally response to client.&lt;br /&gt;&lt;br /&gt;In contrast, in a traditional n-tier application, presentation box are heavily interacting with business objects directly.&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;Why do SOA?&lt;/strong&gt;&lt;br /&gt;I cited Chip’s &lt;a href="http://www.15seconds.com/issue/031215.htm"&gt;Realizing a Service-Oriented Architecture with .NET&lt;/a&gt; here: ‘A good architecture emphasizes a separation of responsibilities. For example, the presentation tier manages presentation components; the business logic tier manages business logic components; and the data access tier manages data access components.’&lt;br /&gt;‘This separation provides for fault tolerance, easier maintenance, and future-proofing. A good service-oriented architecture is nothing new, just a smart way of separating (and exposing) a component's responsibilities.’&lt;br /&gt;Fault tolerance, easier maintenance, and future-proofing are big &lt;a href="http://www.martinfowler.com/ieeeSoftware/marketecture.pdf"&gt;marketecture&lt;/a&gt; buzz words to tell VPs and CIO. Regardless how these words have been abused, they are true in SOA scenario.&lt;br /&gt;In a recent online application project I have worked on, we see these immediate benefits. This is high level description of the archetecture:&lt;br /&gt;&lt;br /&gt;&lt;li&gt;The application form is modelled as an xml schema.&lt;/li&gt;&lt;li&gt;‘Service purple cloud’ is implemented as web service (we will come to that in next section) and associated assemblies.&lt;/li&gt;&lt;li&gt;Request/Response between presentation and middleware (business objects) is via this web service. Transaction orchestration is implemented as part of the purple cloud in the associated assemblies. &lt;/li&gt;&lt;li&gt;Business functions – retrieving customer data, product data, calls to BACS are already existed.&lt;/li&gt;&lt;br /&gt;&lt;br /&gt;The gain is multi-dimensional.&lt;br /&gt;&lt;br /&gt;From presentation (client) point of view, what happens between request-submitted to response-returned is a black box case. We do online transaction at the moment, but we could also dehydrate the application data if some business functions hosting in a different platform down. These are all transparent to the client. And because the only link between client and service is the application XML schema, it is easily accommodate the future needs. Say, we now have presentation supports web client, but if we do Windows Form or B2B whole sale, the same XML schema is suffice without requiring any change to purple cloud and behind it.&lt;br /&gt;&lt;br /&gt;For code implementation point, the development is naturally broken down into more manageable iterations. The first iteration is to implement the application data dehydration. Then we add online transaction capacity in second iteration. Should business process decide to call a stop for iteration 2, the iteration 1 deliverable can still go live without a hinge. (There is a process to extract dehydrated data though, it is needed anyway.)&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;What enables SOA?&lt;/strong&gt;&lt;br /&gt;As you guessed, the key player in SOA is the SOAP and Web Services. In our case study, presentation box validates and serializes application data SOAP message then invokes call to the web service. From presentation point of view, the entire end-to-end business process has only a single point of contact.&lt;br /&gt;&lt;strong&gt;&lt;/strong&gt;&lt;br /&gt;&lt;strong&gt;Compares SOA and OOA&lt;br /&gt;&lt;/strong&gt;SOA is not the Chinese &lt;a href="http://www.china-on-site.com/monkey.php"&gt;monkey king&lt;/a&gt; born out from rock. It evolves from the classic object-oriented architectures.&lt;br /&gt;&lt;br /&gt;In Object-oriented architectures (OOA) paradigm - not sure if this is an establish name, I used it just to contrasting SOA – such like COM, DCOM, RPC, .NET Remoting and etc, ‘objects are marshaled across process boundaries through the proxy/stub techniques… provides benefits such as location transparency.’ (&lt;i&gt;Chip Irek&lt;/i&gt;). This requires stateful objects persisted multiple communication links and lots of plumbing boilerplate codes. These communication links contributes to more tightly coupled architecture between presentation and middleware.&lt;br /&gt;Table is turned in a service-oriented architecture. As you see there is no coupling between presentation and middleware. Clients consume services rather than invoking discreet method calls directly. The result is a loosely coupled system that glued together by contract of SOAP message.&lt;br /&gt;&lt;br /&gt;Don’t get confused by the SOA, OOA and OOAD (as of object-oriented analysis and design). Object-oriented architectures and service-oriented architecture are enterprise architecture patterns while OOAD is the data modeling, programming methodology. SOA doesn’t and shouldn’t defy OOAD in implementing business process – the black box behind the purple cloud.&lt;br /&gt;&lt;br /&gt;&lt;i&gt;On a side note, in last year’ MS PDC in Amsterdam, Don Box informally compared the performance between Remoting and Web Service and the conclusion is web service wins.&lt;/i&gt; 'On ASMX serialization vs. binary serialization with remoting, ASMX will be faster than .NET remoting, short term performance gains using remoting today will not position your applications for future releases'. Read it &lt;a href="http://weblogs.asp.net/shawnmor/archive/2004/05/27/143209.aspx"&gt;here&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;SOA Design Issue&lt;/strong&gt;&lt;br /&gt;Having said the OOAD can be applied, it doesn’t mean there is absolutely not changes in the design patterns. I reckon the biggest challenge is to design the application as composed of stateless components while it still provides a rich customer experience. Get back to the online application process in our case study, the application data should be a modelled against its paper based cousin. It should be self –described. So anyone picks it up can process it without restoring help from other system.&lt;br /&gt;&lt;br /&gt;I cite (again) Chip Irek to conclusion how to effectively implement SOA design: &lt;i&gt;‘Web methods should be designed to perform an entire service for an entire form.&lt;/i&gt;&lt;br /&gt;&lt;br /&gt;Reference:&lt;br /&gt;Chip Irek: &lt;a href="http://www.15seconds.com/issue/031215.htm"&gt;Realizing a Service-Oriented Architecture with .NET&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;Further Reading:&lt;br /&gt;Dave Chappell &lt;a href="http://www.oreillynet.com/pub/wlg/6444"&gt;Extracting Business Value from SOA&lt;/a&gt;&lt;br /&gt;James Greenwood &lt;a href="http://weblogs.asp.net/jsgreenwood/archive/2004/10/17/243639.aspx"&gt;SOA Design with Agile methodologies&lt;/a&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-111010532965550457?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/111010532965550457/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=111010532965550457' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/111010532965550457'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/111010532965550457'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2005/03/service-oriented-architectures-soa.html' title='Service-Oriented Architectures (SOA)'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-111005771590995974</id><published>2005-03-05T21:21:00.000Z</published><updated>2006-11-01T12:27:41.555Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='not work'/><title type='text'>Fun and not so fun stuff about techie interview</title><content type='html'>Chris Sells collected a bunch of &lt;a href="http://www.sellsbrothers.com/fun/msiview/"&gt;Microsoft Interview Questions&lt;/a&gt; Manhole is the new classic. I wish my boss could ask me that in my next internal review.&lt;br /&gt;&lt;br /&gt;Mike Woood has some excellent questions to 'strike' back (&lt;a href="http://mvwood.com/Blog/articles/255.aspx"&gt;How to ask questions at your interview...or which questions to ask&lt;/a&gt;)What type of work is more prevalent at the company currently? How much project work is there? How much .Net? What are the goals of the company? ...&lt;br /&gt;Observe their body language on above most 'interesting' questions.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-111005771590995974?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/111005771590995974/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=111005771590995974' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/111005771590995974'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/111005771590995974'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2005/03/fun-and-not-so-fun-stuff-about-techie.html' title='Fun and not so fun stuff about techie interview'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-111022923411082441</id><published>2005-03-05T21:00:00.000Z</published><updated>2006-11-01T12:29:11.363Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='web service'/><title type='text'>Why WSE?</title><content type='html'>WSE Executive Summary&lt;br /&gt;&lt;br /&gt;&lt;li&gt;Free. Save your investment on in-house development of WS-specifications framework or 3rd part product, such like GetAccess&lt;/li&gt;&lt;br /&gt;&lt;li&gt;Current release is guaranteed side-by-side compatible with future releases, thanks .net framwork&lt;/li&gt;&lt;br /&gt;&lt;li&gt;Message is end2end secured. This is in contrast to transport protocol or wire level security (e.g. HTTPS, SSL). It can be used for many different protocols such as SMTP, FTP, and TCP &lt;/li&gt;&lt;br /&gt;&lt;br /&gt;What has been acheive?&lt;br /&gt;&lt;li&gt;Message Integrity&lt;/li&gt; it uses XML Digital Signatures.&lt;br /&gt;&lt;li&gt;Confidentiality&lt;/li&gt; is based on the XML Encryption specification&lt;br /&gt;&lt;li&gt;Authentication&lt;/li&gt; It uses security token that embeds in SOAP header to identify a caller.&lt;br /&gt;&lt;br /&gt;For demo and more information read this:&lt;a href="http://msdn.microsoft.com/webservices/default.aspx?pull=/library/en-us/dnwse/html/whywse.asp?_r=1"&gt;Web Services Home: Why WSE?&lt;/a&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-111022923411082441?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='related' href='http://msdn.microsoft.com/webservices/default.aspx?pull=/library/en-us/dnwse/html/whywse.asp?_r=1' title='Why WSE?'/><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/111022923411082441/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=111022923411082441' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/111022923411082441'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/111022923411082441'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2005/03/why-wse.html' title='Why WSE?'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-110997914687907746</id><published>2005-03-04T19:03:00.000Z</published><updated>2006-11-01T12:24:16.818Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='vs.net'/><title type='text'>Import/Export VS.Net keybinding shortcut mappings</title><content type='html'>Every time a new Visual Studio released there are changes to the key binding or shortcut key mappings. Vs.NET 2005 seemed make sense than its predecessors as it introduces command themes and use chords (e.g. Ctrl+k, ctrl+c) instead of three-key shortcuts (Ctrl+Shift+b), as discussed in JoeN's Blog &lt;a href="http://blogs.msdn.com/joen/archive/2004/06/10/153245.aspx"&gt;So why did the C# keybindings change?&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;But it just annoying when everytime move to a new developement box, I have to reassign the keybings from Tools(Menu) Customize Keyboard...(button). At the moment I am fine on stealing my beloved box when I moved to new team without being caught by security cameras (there are two in the office known to me :-) ). Would it be great if I can just export the profile and import it to the new IDE? Seen a really straight forward idea, but VS.NET doesn’t offer you such function.&lt;br /&gt;&lt;br /&gt;As I am car-sharing with Jim and he is still fiddling on live release (Friday, 18:30 pm) I am in the mood for a little experiment.&lt;br /&gt;&lt;br /&gt;After a few searches, I found Joel Ross wrote a blog &lt;a href="http://blogs.sagestone.net/jross/archive/2004/04/22/187.aspx"&gt;Saving VS.NET Settings&lt;/a&gt; on how to do it. The article also covers saving setting for Window Layouts, Toolbar\Menu Configurations, Customized Toolbox Settings and other Add-ins settings. For now saving a copy of keybindings and &lt;a href="http://beta.blogger.com/www.jetbrains.com/resharper/"&gt;ReSharper &lt;/a&gt;will serve me well.&lt;br /&gt;&lt;br /&gt;Task 1 Export/import custom Keybindings:&lt;br /&gt;&lt;li&gt;Create Custom Keybindings: Launch an instnace of VS.NET. Then click Tools(Menu) | Customize | Keyboard...(button on the pop-out property window). This will open the Options window.&lt;/li&gt;&lt;br /&gt;&lt;li&gt;Assign shortcuts to commands as you wish. I select the &lt;a href="http://www.blogger.com/"&gt;Reflector add-in&lt;/a&gt; command: &lt;span class="codesnippet"&gt;Reflector.ManageAddIn.Connect.Diassembler.CSharpCommand&lt;/span&gt; and assignit ALT+T,I&lt;/li&gt;&lt;br /&gt;&lt;li&gt;Save the Keyboard mapping secheme as a new seheme using the "Save as" button. I save it as Jingye keybindings&lt;/li&gt;&lt;br /&gt;&lt;li&gt;Click OK to close the Option window. Then close the Customize window. Close the VS.NET instance so the setting saved to your personal VS AppData directory&lt;/li&gt;&lt;br /&gt;&lt;li&gt;Use windows file expolorer to go to your AppDara directory: &lt;i&gt;“\Documents and Settings\%Current User%\Application Data\Microsoft\VisualStudio\7.1\”&lt;/i&gt;&lt;/li&gt;&lt;br /&gt;&lt;li&gt;In this directory you will find a file called: &lt;i&gt;"Jingye keybindings.vsk"&lt;/i&gt;, it contains the shortcuts just created.&lt;/li&gt;&lt;br /&gt;&lt;li&gt;Copy and take it to another development machine, still put it in the same directory. If this directory is not existed, create it as &lt;i&gt;“\Documents and Settings\%Current User%\Application Data\Microsoft\VisualStudio\7.1\”&lt;/i&gt;&lt;/li&gt;&lt;br /&gt;&lt;li&gt;Launch an instance of VS.Net on this machine, and select "Jingye keybindings" from Tools(Menu) | Customize | Keyboard...(button)| Keyboard mapping secheme (drop down list)&lt;/li&gt;&lt;br /&gt;&lt;br /&gt;Now the new shortcut [ALT+T] [ALT+I] can be used on the new environment.&lt;br /&gt;&lt;br /&gt;While doing this I notice there are a folder "JetBrains" in the “\Documents and Settings\%Current User%\Application Data\". Guess can move the ReSharper profile I assigned in a similar way.&lt;br /&gt;&lt;br /&gt;Task 2 Export/import ReSharper user profile/options.&lt;br /&gt;&lt;li&gt;ReSharper adds a "ReSharper" menu to the VS.NET IDE. You can change the default setting with "Options..." sub-menu. Such like code style, code completion, etc. &lt;/li&gt;&lt;br /&gt;&lt;li&gt;The user settings is saved to &lt;i&gt;“\Documents and Settings\%Current User%\Application Data\JetBrains\ReSharper\UserSettings.xml"&lt;/i&gt; once you close the VS.net instance.&lt;/li&gt;&lt;br /&gt;&lt;li&gt;The UserSettings.xml contains all configurable settings including code style, intellisense, as well as license key. You can port this file to a different user profile or developement box, but be careful and stay at the right side with the license agreement. Guys work on this deserve every respect of it.&lt;/li&gt;&lt;br /&gt;&lt;br /&gt;I am still waiting for Jim to complete the release... :-(&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-110997914687907746?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/110997914687907746/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=110997914687907746' title='2 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/110997914687907746'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/110997914687907746'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2005/03/importexport-vsnet-keybinding-shortcut.html' title='Import/Export VS.Net keybinding shortcut mappings'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><thr:total>2</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-110997832041008147</id><published>2005-03-01T21:01:00.000Z</published><updated>2006-11-01T12:25:45.545Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='vs.net'/><title type='text'>vs.net developer's toolbox</title><content type='html'>I used to love playing PC RPG game such like &lt;a href="http://www.gameqt.com/shop/product_info.php?cPath=21_67&amp;products_id=1379&amp;amp;osCsid=56be3f28ca28b356ce7bddcf44e75c35"&gt;The Magic Sword &amp;amp; The Chivalrous Youngsters&lt;/a&gt;. Player impersonates a Kongfu master and experiences the life of JiangHu(lives of the 'gang ring' and dark society). Typically you start with a junior level and knowing very little about martial art weapon and armour art master. Then you start learning from other masters and pick up some ‘Kongfu Sutra’ and practicing yourself. You will be on assignments, such like escort a convoy through treacherous terrain or to steal a treasure chest from the royal palace etc. In these assignments you will found lots o gem or little secret chest. Pick it up, and some are powerful weapons that require practicing. Some are secret potions that will grant you transit magic power. Inevitably by the time the game ends, you are a grown Kongfu master.&lt;br /&gt;&lt;br /&gt;Similarly, there are VS.Net add-ins tools to the IDE that help us more to be more productive and write better code. I think part of the fun of it is to find the add-ins, install it, evaluate the usefulness, assigned the keyboard shortcuts and being familiar on using them without mouse click. In pair programming, it is just amused to play the trick and see the look on your peer’s face: ‘how do you do that?’ (VS.net 2005 has incorporate many of these add-in features such like TestDriven.net or code refactoring :-) ).&lt;br /&gt;&lt;br /&gt;Order in weight of importance, I feel these tools are must have (some of them are not really VS.NET addins but just powerful tools):&lt;br /&gt;&lt;ul&gt;&lt;br /&gt;&lt;li&gt;Google tool bar, save you many clicks and key stokes to go to it’s home page.&lt;/li&gt;&lt;br /&gt;&lt;br /&gt;&lt;li&gt;&lt;a href="http://beta.blogger.com/www.nunit.org"&gt;nUnit&lt;/a&gt; + &lt;a href="http://www.testdriven.net/"&gt;TestDriven.Net&lt;/a&gt;&lt;/li&gt;(an very cool nUnit addin to VS.NET that enables inline unit test and debugging without leaving the IDE.&lt;br /&gt;&lt;br /&gt;&lt;li&gt;&lt;a href="http://www.jetbrains.com/resharper/"&gt;ReSharper&lt;/a&gt;.&lt;/li&gt; Code refactoring and code reformat are the two I used most.&lt;br /&gt;&lt;br /&gt;Sometimes object browser is just not enough. A spycam would be useful:&lt;br /&gt;&lt;li&gt;&lt;a href="http://www.aisto.com/roeder/dotnet/"&gt;Lutz Roeder's .Net Reflector&lt;/a&gt; + &lt;a href="http://www.freewebs.com/csharp/Reflector/AddIns/"&gt;Reflector Addins&lt;/a&gt;.&lt;/li&gt;The one I use most is the &lt;a href="http://www.testdriven.net/"&gt;Reflector.VisualStudio&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;&lt;li&gt;In a team enviroment &lt;a href="http://confluence.public.thoughtworks.org/display/CCNET/What+is+CruiseControl.NET"&gt;CruiseControl.net&lt;/a&gt; is the most important tool for code shared check-out and &lt;a href="http://www.martinfowler.com/articles/continuousIntegration.html"&gt;continuous integration(CI)&lt;/a&gt;.&lt;/li&gt; It reads an nAnt script and do whatever commandline tasks it is told. Monitoring code repository, build solution with VS.net (devenv), run all unit test etc. There are also a system tray client appicon (CCtray) sends notifications on build state.&lt;br /&gt;&lt;br /&gt;&lt;li&gt;&lt;a href="http://ncover.sourceforge.net/"&gt;nCover&lt;/a&gt; should also be considered as part of the nAnt task in your continuous integration(CI)&lt;/li&gt; In the dev environment I am working, we have an uber code integration build server and many team and projects are contributing to the same code repository. Our team was quite proud to bring the 'green bar' from 11% to 53%.  &lt;a href="http://dotnetjunkies.com/WebLog/alan.dean/archive/2004/08/20/22748.aspx"&gt;Alan Dean compares&lt;/a&gt; the usefulness of nCover and &lt;a href="http://www.gotdotnet.com/Community/UserSamples/Details.aspx?SampleGuid=881a36c6-6f45-4485-a94e-060130687151"&gt;CoverageEye.net&lt;/a&gt; in commandline mode. I haven't tried the CoverageEye.net for the CI.&lt;br /&gt;&lt;br /&gt;&lt;li&gt;&lt;a href="http://www.blunck.info/iehttpheaders.html"&gt;ieHTTPHeader&lt;/a&gt;&lt;/li&gt; an explorer bar for Internet Explorer that will show you the HTTP Headers IE are sending and receiving. Quite useful at ASP.NET web app debugging.&lt;br /&gt;&lt;br /&gt;&lt;li&gt;&lt;a href="http://www.sellsbrothers.com/tools/#regexd"&gt;Chris Sells' RegexDesigner.NET&lt;/a&gt; A very inspiring regex composer, helps a lot on learning reguar expression.&lt;/li&gt;&lt;br /&gt;&lt;br /&gt;&lt;li&gt;&lt;a href="http://ndoc.sourceforge.net/"&gt;nDoc&lt;/a&gt; Your PA for documentation, taking awful longtime to run but works well.&lt;/li&gt;The good news is you don't have to run it until next release.&lt;br /&gt;&lt;br /&gt;&lt;li&gt;Albeit the not very smart name &lt;a href="http://www.gotdotnet.com/team/fxcop/"&gt;FxCop&lt;/a&gt;&lt;/li&gt; does help the development team on code review. Sometimes I find it is quite daunting to click the analysis button particularly newbies on .NET. We started with runing it as part of continous integration, then disabling a few rules and endup with running it for code review only.&lt;br /&gt;&lt;br /&gt;Last but not least the &lt;li&gt;&lt;a href="http://www.bmtmicro.com/BMTCatalog/win/merge2000.html"&gt;Araxis Merge Tool&lt;/a&gt;.  Similar to windiff just 100 times better. ASCII, binary and recursive comparison on file system. You can specify multiple regex to by-pass trivial things like comment. Last time we use it for code migration on 100+ java packages with more than 800 classes, which coupling with live binaries version identification. It helped a lot.&lt;br /&gt;&lt;/li&gt;&lt;/ul&gt;&lt;br /&gt;I may have missed some but these are the most important tools to me. Once get them running, the next step it to hook them into VS.NET using Add-manager. Then assign keyboard mappings and be familiar with them.&lt;br /&gt;&lt;br /&gt;It won't be long before you call mouse as the WMD (Weapon of Mass Distraction)&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-110997832041008147?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/110997832041008147/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=110997832041008147' title='2 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/110997832041008147'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/110997832041008147'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2005/03/vsnet-developers-toolbox.html' title='vs.net developer&apos;s toolbox'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><thr:total>2</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-110961209031209151</id><published>2005-02-28T17:34:00.000Z</published><updated>2006-11-01T12:29:23.621Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='.net'/><category scheme='http://www.blogger.com/atom/ns#' term='xml'/><title type='text'>Debug into a .NET XmlSerializer Generated Assembly</title><content type='html'>Scott Hanselman got a nice trick to&lt;br /&gt;&lt;a href="http://www.hanselman.com/blog/PermaLink.aspx?guid=4185d5c5-17ab-4ed6-b934-e244b9895b4c"&gt;Debug into a .NET XmlSerializer Generated Assembly&lt;/a&gt; object Serialization using XmlSerializer. The temparary generated cs file need to open in the same IDE and being set the break point to while the debugging session is on.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-110961209031209151?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='related' href='http://www.hanselman.com/blog/PermaLink.aspx?guid=4185d5c5-17ab-4ed6-b934-e244b9895b4c' title='Debug into a .NET XmlSerializer Generated Assembly'/><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/110961209031209151/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=110961209031209151' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/110961209031209151'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/110961209031209151'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2005/02/debug-into-net-xmlserializer-generated.html' title='Debug into a .NET XmlSerializer Generated Assembly'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-110958383676087414</id><published>2005-02-28T09:43:00.000Z</published><updated>2006-11-01T12:29:31.509Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='.net'/><title type='text'>What Great .NET Developers Ought To Know</title><content type='html'>Will try some quizz later:&lt;br /&gt;&lt;a href="http://www.hanselman.com/blog/WhatGreatNETDevelopersOughtToKnowMoreNETInterviewQuestions.aspx"&gt;ComputerZen.com - Scott Hanselman's Weblog - What Great .NET Developers Ought To Know&lt;/a&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-110958383676087414?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='related' href='http://www.hanselman.com/blog/WhatGreatNETDevelopersOughtToKnowMoreNETInterviewQuestions.aspx' title='What Great .NET Developers Ought To Know'/><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/110958383676087414/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=110958383676087414' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/110958383676087414'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/110958383676087414'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2005/02/what-great-net-developers-ought-to.html' title='What Great .NET Developers Ought To Know'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-110958375516981677</id><published>2005-02-28T09:42:00.000Z</published><updated>2006-11-01T12:29:39.692Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='not work'/><title type='text'>Tips for doing effective Presentations</title><content type='html'>A resolution of the year: have a good work out on the presentation skills. This article offers great tips.&lt;br /&gt;&lt;a href="http://www.venkatarangan.com/blog/PermaLink.aspx?guid=dab57735-2976-40d7-a5d0-2e641ddea515"&gt;Venkatarangan's Blog [???????????? ??????????] - Tips for doing effective Presentations&lt;/a&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-110958375516981677?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='related' href='http://www.venkatarangan.com/blog/PermaLink.aspx?guid=dab57735-2976-40d7-a5d0-2e641ddea515' title='Tips for doing effective Presentations'/><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/110958375516981677/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=110958375516981677' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/110958375516981677'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/110958375516981677'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2005/02/tips-for-doing-effective-presentations.html' title='Tips for doing effective Presentations'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-110142529745528296</id><published>2004-11-25T23:28:00.000Z</published><updated>2006-11-01T12:29:45.926Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='asp.net'/><title type='text'>ASP.NET page life cycle</title><content type='html'>Paul Wilson's article &lt;a href="http://aspalliance.com/articleViewer.aspx?aId=134&amp;amp;pId="&gt;Page Events: Order and PostBack&lt;/a&gt;&lt;br /&gt;and Dino Esposito's&lt;br /&gt;&lt;a href="http://msdn.microsoft.com/asp.net/default.aspx?pull=/library/en-us/dnaspp/html/aspnet-pageobjectmodel.asp"&gt;The ASP.NET Page Object Model&lt;/a&gt; are good reminders for questions like 'When does this (server-side) Textbox validation happen?' and 'Where do I assign the regular expression for validator?'&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-110142529745528296?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='related' href='http://aspalliance.com/articleViewer.aspx?aId=134&amp;pId=' title='ASP.NET page life cycle'/><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/110142529745528296/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=110142529745528296' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/110142529745528296'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/110142529745528296'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2004/11/aspnet-page-life-cycle.html' title='ASP.NET page life cycle'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-110130353657140259</id><published>2004-11-24T13:38:00.000Z</published><updated>2006-11-01T12:29:56.805Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='not work'/><title type='text'>Yet another Microsoft Exam</title><content type='html'>Now I am a MCAD! This time I am taking on '070-229 Designing and Implementing Databases with Microsoft SQL Server 2000 Enterprise Edition' with the help from Professional SQL Server 2000 Programming, by R, Viera. Persnally, I don't like the book. The concepts and practices in each chapter is very loose. It is at lack of structural way of presenting idea. And it will be better if Viera is not using overly verbal language and side-tracking jokes. It will be more painless to read if it can be more concise. I found using Sql Server Book On Line offers great help.&lt;br /&gt;&lt;br /&gt;Anyway it covers everything and it is a seriously huge book. My day bag is much lighter now.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-110130353657140259?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/110130353657140259/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=110130353657140259' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/110130353657140259'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/110130353657140259'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2004/11/yet-another-microsoft-exam.html' title='Yet another Microsoft Exam'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-110086131412713847</id><published>2004-11-19T10:48:00.000Z</published><updated>2006-11-01T12:30:09.429Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='.net'/><title type='text'>ADO.NET and SQL Server security, performance Recommendations</title><content type='html'>The typical application scenario is an internet web application located in DMZ then submits data via ADO.NET, either in-process or though middle tier.&lt;br /&gt;&lt;br /&gt;1. Use windows authentication.&lt;br /&gt; 1)  The web server should not be in the trusted domain. Create a local NT user account ‘Fred’ with least privileges. This account will be used as the IIS anonymous access account for the web application.&lt;br /&gt; 2)  Enable IIS anonymous access for the web application.&lt;br /&gt; 3)  On the Sql Server, mirror the NT account ‘Fred’ created above. Set Sql Server security login mode to be ‘Windows Only’.&lt;br /&gt; 4)  Create a SQL Server Login for ‘Fred’. Grant ‘Fred’ to ‘Public’, ‘Deny Data Reader’ and ‘Deny Data Writer’ access.&lt;br /&gt; 5)  Allow application access data via Store Procedures only. Grant ‘Fred’ to all user- defined store procedures exec rights.&lt;br /&gt;&lt;br /&gt;2.When you specify a server in an ADO.NET connection string, always use IP address instead of the server's DNS name to cut the overhead on DNS resolution.&lt;br /&gt;&lt;br /&gt;3.Specify 'Application Name' in the connection string. It makes SQL Profiler can pick up the connections quite handy, or just for trouble-shooting.&lt;br /&gt;&lt;br /&gt;4.Do not use SQL Server application roles, it turns off connection pooling.&lt;br /&gt;&lt;br /&gt;5.When possible, use the ExecuteNonQuery method with SQLCommand objects, as this is the most efficient way to execute queries from ADO.NET. Use output parameters with SQLCommand objects if you need to retrieve just a few values, or a single data row, instead of using more expensive techniques, such as a SQLDataAdapter, a SQLDataReader, or a strongly typed DataSet.&lt;br /&gt;&lt;br /&gt;6.Avoid using Transact-SQL cursor at all possible, try use correlated sub-query or temporary table instead.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-110086131412713847?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/110086131412713847/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=110086131412713847' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/110086131412713847'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/110086131412713847'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2004/11/adonet-and-sql-server-security.html' title='ADO.NET and SQL Server security, performance Recommendations'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-110073578057461029</id><published>2004-11-17T23:33:00.000Z</published><updated>2006-11-01T12:30:22.019Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='vs.net'/><title type='text'>My new soruce control client hijacks Visual Studio default soruce control provider</title><content type='html'>The default source control provider links to Visual Studio is VSS (of course!). Howerver, since I installed PVCS Dimesion client for a different project recently, the source control changed to be PVCS.&lt;br /&gt;It is not in my interest to use PVCS for the .NET projects I am working on. However, there is no way you can change it back to VSS from Visual Studio(it is not the tools|option|source safe menu.)&lt;br /&gt;The only way to change this is from registry:&lt;br /&gt;&lt;br /&gt;Run regedit. Browse to 'HKEY_LOCAL_MACHINE\SOFTWARE\SourceCodeControlProvider\InstalledSCCProviders', it should be a list of all installed SC providers there. Copy the Data (path) of the intended used source control provider, then use it to replace data of 'HKEY_LOCAL_MACHINE\SOFTWARE\SourceCodeControlProvider\ProviderRegKey'.&lt;br /&gt;&lt;br /&gt;Maybe there is a switch program around? Sure I am not the first one met this problem. I will do one if I have time. Many thanks to Nick A. to share this.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-110073578057461029?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/110073578057461029/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=110073578057461029' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/110073578057461029'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/110073578057461029'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2004/11/my-new-soruce-control-client-hijacks.html' title='My new soruce control client hijacks Visual Studio default soruce control provider'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-110064777248985066</id><published>2004-11-16T23:29:00.000Z</published><updated>2006-11-01T12:30:27.229Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='sql'/><title type='text'>Setting Up Trusted Connection between Sql Server and Web Server</title><content type='html'>Initiatives: MS Pattern and Practices recommendation: Building Secure ASP.NET Applications: Authentication, Authorization, and Secure Communication:&lt;br /&gt;&lt;a href="http://msdn.microsoft.com/library/default.asp?url=/library/en-us/dnnetsec/html/SecNetch06.asp"&gt;Extranet Security&lt;/a&gt; and &lt;a href="http://msdn.microsoft.com/library/default.asp?url=/library/en-us/dnnetsec/html/SecNetch12.asp"&gt;Access Security&lt;/a&gt;.&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;Scenario 1 SqlServer and Web Server are running on the same box&lt;/strong&gt;&lt;br /&gt;Likely be the home pc or standalone development environment-the configuration is quite simple:&lt;br /&gt;&lt;strong&gt;1. IIS6 (Windows 2003 Server)&lt;/strong&gt;&lt;br /&gt;Follow this &lt;a href="http://www.asp.net/faq/AspNetAndIIS6.aspx#4"&gt;article&lt;/a&gt; to configurate IIS 6 access to SqlServer.&lt;br /&gt;In my experiments, it shows that the IIS anonymous account setting in the web app's '(Virtual) Directory Security setting | Authentication and access control' and disable/enable integrate Windows authentication is not relevant- it will always be an IIS_WPG member account used to access SqlServer. You can run &lt;span class="codesnippet"&gt;EXEC sp_who&lt;/span&gt; to find out which account is used.&lt;br /&gt;&lt;br /&gt;The only exception to above is you specify &lt;span class="codesnippet"&gt;&amp;lt;identity impersonate="true"/&amp;gt;&lt;/span&gt; in web.config. I tried to use IUSER_&lt;machinename&gt;(Internet Guest Account). However, it failed to get access to Sql Server (SP3)mysteriously, even I have grant the correct access rights to it.&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;2. IIS5 (Windows 2000 Server)&lt;/strong&gt;&lt;br /&gt;If running on IIS5(Windows 2000)it is IUSER_&lt;machinename&gt; used as the anonymous account. I guess it will be fine to use it to access SqlServer. Will try out soon. At the end of this blog is a vbs script which shows the credentials of IIS anonymous account and ASPNET Procs account.&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;Scenario 2 SqlServer and Web Server are running on two machines&lt;/strong&gt;&lt;br /&gt;In short, the MS recommended way is:&lt;br /&gt;1)Don't put Web server on the trusted domain, but DMZ.&lt;br /&gt;2)Create a NT account that impersonate as IIS anonymous account on web server.&lt;br /&gt;3)Create the exact same account(username/password) on the Sql Server machine.&lt;br /&gt;4)Grant access to this account.&lt;br /&gt;&lt;br /&gt;&lt;a href="http://weblogs.asp.net/AChang/archive/2004/04/15/113866.aspx"&gt;How to use Trusted Connection when SQL server and web Server are on two separate machines&lt;/a&gt; has step by step guide on this.&lt;br /&gt;&lt;br /&gt;Following vbs script shows credentials for iis anonymous user account&lt;br /&gt;&lt;/machinename&gt;&lt;/machinename&gt;&lt;div class="code"&gt;&lt;br /&gt;Dim IIsObject&lt;br /&gt;Set IIsObject = GetObject ("IIS://localhost/w3svc")&lt;br /&gt;WScript.Echo "AnonymousUserName = " &amp; IIsObject.Get("AnonymousUserName") &amp;amp; vbCrlf&lt;br /&gt;WScript.Echo "AnonymousUserPass = " &amp; IIsObject.Get("AnonymousUserPass") &amp;amp; vbCrlf&lt;br /&gt;WScript.Echo "WAMUserName = " &amp; IIsObject.Get("WAMUserName") &amp;amp; vbCrlf&lt;br /&gt;WScript.Echo "WAMUserPass = " &amp;amp; IIsObject.Get("WAMUserPass")&lt;br /&gt;Set IIsObject = Nothing&lt;br /&gt;&lt;/div&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-110064777248985066?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='related' href='http://weblogs.asp.net/AChang/archive/2004/04/15/113866.aspx' title='Setting Up Trusted Connection between Sql Server and Web Server'/><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/110064777248985066/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=110064777248985066' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/110064777248985066'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/110064777248985066'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2004/11/setting-up-trusted-connection-between.html' title='Setting Up Trusted Connection between Sql Server and Web Server'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-109765816803125406</id><published>2004-10-13T09:59:00.000+01:00</published><updated>2006-11-01T12:30:32.595Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='win server'/><title type='text'>Biztalk Resource:</title><content type='html'>Valuble Biztalk Resource:&lt;br /&gt;&lt;a href="http://blogs.msdn.com/biztalk_core_engine/archive/2004/09/20/231974.aspx"&gt;Biztalk MessageBox Advance Queries&lt;/a&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-109765816803125406?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='related' href='http://blogs.msdn.com/biztalk_core_engine/archive/2004/09/20/231974.aspx' title='Biztalk Resource:'/><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/109765816803125406/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=109765816803125406' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/109765816803125406'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/109765816803125406'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2004/10/biztalk-resource.html' title='Biztalk Resource:'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-109748846827955139</id><published>2004-10-11T10:51:00.000+01:00</published><updated>2006-11-01T12:30:38.942Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='not work'/><title type='text'>week two at MTC(Microsof Technoloy Center)</title><content type='html'>We have been here for two weeks to work with MS technologists on a Biztalk proof of concept project for our B2B system integration. I finally can spare sometime to do some brain dump.&lt;br /&gt;We completed most of the development tasks for the POC. The opened issues here are around testing and some deployment setups for non-core services.&lt;br /&gt;Phil (card ops), Geoff and Ade visited us on Thursday for a mid-term work check. They seemed quite satisfied about what Biztalk can do and how Biztalk can be used by the non-technologist. We even got Phil to create and test an orchestration with his own hand on the mouse.&lt;br /&gt;The most interesting bit is deployment automation. Biztalk Deployment is a daunting task:&lt;br /&gt;First you need to deploy .NET assemblies to GAC (these assemblies typically provide utility functions that used by orchestrations, rules engine, custom pipelines).&lt;br /&gt;Then install all custom adapters if they are not previously installed on the machine. HTTP, SOAP, MSMQ etc are provided as standard, we also got a Topend adapter.&lt;br /&gt;Then install the business rules engine.&lt;br /&gt;Then install all Biztalk assemblies.&lt;br /&gt;Then install and bind all send/receive ports Biztalk assemblies used.&lt;br /&gt;Then start all orchestrations.&lt;br /&gt;For our development and demo, we also need to install all web services used by Biztalk such like Smart Connectors and web sites for demonstration.&lt;br /&gt;&lt;br /&gt;And of course we need a clean up script to reverse the deployment as well- it takes a whole lot to test a Biztalk orchestration.&lt;br /&gt;&lt;br /&gt;We use command line script to automate these tasks. Some of them are provided in the SDK samples, others are not. Such like deploying business rules. Before we come to Reading, even MS are telling people ‘It is very difficult to automate this step, and you are better off to use the GUI wizard to do it’. And now we have a little command line program to do the job!&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-109748846827955139?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/109748846827955139/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=109748846827955139' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/109748846827955139'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/109748846827955139'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2004/10/week-two-at-mtcmicrosof-technoloy.html' title='week two at MTC(Microsof Technoloy Center)'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-109603199474508608</id><published>2004-09-24T14:19:00.000+01:00</published><updated>2006-11-01T12:30:45.124Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='win server'/><title type='text'>BizTalk FAQ</title><content type='html'>I am working on a Biztalk POC project at the moment, here is a list of problems have occurred to me at varuious stage and the solutions. The list will keep growing as proceeding.&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;1. Biztalk Message Queue causes conflict with MSMQ&lt;/strong&gt;&lt;br /&gt;-- In short, you cannot run MSMQT on the same machine as MSMQ runs. What behind MSMQT is MSMQ, they are using the same port (1801). This can happen on the test/deployment machine if MSMQ already run then you configure to use MSMQT. This problem raised when you try to start Biztalk Application again.. Stop the MSMQ service (Message Queuing and Message Queuing Triger) from Service Control Console, then start the Biztalk Application will fix the problem.&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;2. Running an independet web service on the same development machine that has biztalk server and Sharepoint server installed. I was getting 404 'file not found' when requesting a web service.&lt;/strong&gt;&lt;br /&gt;--MS Development team suggest the stsfltr.dll ISAPI filter from sharepoint team services may cause the problem. I have tried remove this ISAP filter from IIS, problem solved. Read this &lt;a href="http://support.microsoft.com/default.aspx?scid=kb;en-us;823265"&gt;KB&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;3. I drop the request xml into the receive port-bound dir, it has been processed but the resulted xml doc is not produced, why?&lt;/strong&gt;&lt;br /&gt;--  It is spot on that orchestration process picks up the request as it has been removed from receive port-bound dir. The first thing to check is the send port - outbound settings. Is the dir granted with appropriate write/modify access to the account that BiztalkServerApplication runs under? Is there any typo in the address URL send ports point to?&lt;br /&gt;If you are using late bound, the problem is easy to rectify. Just stop the orchestration process, unlist it, correct the problem and restart the orchestration process- make sure all receive and send ports and enabled/started.&lt;br /&gt;If the application is bound at the design time, there are few more things need to be done.&lt;br /&gt;First on the development pc, open the source project, correct the problems and rebuild it.&lt;br /&gt;Then on the deployment server, stop/unlist the problematic orchestration from the Biztalk admin console.&lt;br /&gt;Then start the deploy wizard, remove the problematic biztalk assembly from the configuration database-you need to remove it from GAC as well.&lt;br /&gt;Install the new compiled biztalk assembly.&lt;br /&gt;Specify all late bind ports to the new orchestration process use Biztalk Explorer.&lt;br /&gt;Enlist and start the orchestration process  from Biztalk Admin console&lt;br /&gt;&lt;br /&gt;&lt;em&gt;Lesson learn: Always use late binding ports when permitted.&lt;/em&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-109603199474508608?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='related' href='http://www.talkaboutsoftware.com/group/microsoft.public.biztalk.general/messages/10694.html' title='BizTalk FAQ'/><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/109603199474508608/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=109603199474508608' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/109603199474508608'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/109603199474508608'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2004/09/biztalk-faq.html' title='BizTalk FAQ'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-109595660500465338</id><published>2004-09-23T17:23:00.000+01:00</published><updated>2006-11-01T12:30:50.921Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='asp.net'/><title type='text'>ASP.NET Response.Redirect Server.Transfer Server.Execute not working</title><content type='html'>&lt;strong&gt;The symptom: &lt;/strong&gt;&lt;br /&gt;On completion of registration or login, I want to redirect the response to the page where user coming from, say default.aspx. I expect the QueryString ReturnUrl will be picked up and browser will be forwarded.  However, the redirection is not working, working intermittently. Sometimes, the login page stayed as if not being refreshed, other times I got a blank page with url poited to the desired target. I have tried these methods Response.Redirect Server.Transfer Server.Execute and FormsAuthentication.RedirectFromLoginPage. None of them works. I was using Framework 1.1.&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;The solution: &lt;/strong&gt;&lt;br /&gt;1) Make sure your browser supports cookie. If you are using personal proxy, such like ZoneAlarm, check to see it will not block cookies even from localhost.&lt;br /&gt;2) Check to see SmartNevigation is set to off in the web.config. If it is on, the page redirection will fail. Debug trace shows the Application_BeginRequest wouldn’t  even be hit.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-109595660500465338?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/109595660500465338/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=109595660500465338' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/109595660500465338'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/109595660500465338'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2004/09/aspnet-responseredirect-servertransfer.html' title='ASP.NET Response.Redirect Server.Transfer Server.Execute not working'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-109491030584116079</id><published>2004-09-11T14:45:00.000+01:00</published><updated>2006-11-01T12:31:00.040Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='win server'/><title type='text'>CMS SCA Host Headers Mapping vs IIS HTTP Host Headers Mapping</title><content type='html'>MCMS Server Configuration Application (SCA) has an option to map channel names to host headers names. It can be used to allow host multiple CMS web sites with different domain names on the same CMS server.&lt;br /&gt;To do this, we need to map top-level channels as the root channels for a URL with a host header name that is identical to the channel name. When CMS generates a URL pointing to an item inside the virtual site www.CMSsite1.com, it prefixes the URL with the name of the channels in which it is contained.’ See chapter 18 of  book &lt;a href="http://www.amazon.co.uk/exec/obidos/ASIN/0321194446/"&gt; Microsoft Content Management Server 2002 &lt;/a&gt;&lt;br /&gt;There are two points need to note:&lt;br /&gt;1. Names of top channels on a CMS server must match the virtual site names in IIS.&lt;br /&gt;2. The virtual site names must be valid DNS name.&lt;br /&gt;&lt;br /&gt;So a typical co-hosting configuration for three web applications on a development box can be:&lt;br /&gt;&lt;br /&gt;In MCMS Site Manager:&lt;br /&gt;We have three top channels, they sharing the same CMS database, and named as:&lt;br /&gt;www.CMSsite1.com&lt;br /&gt;-------------Product&lt;br /&gt;-------------Service&lt;br /&gt;www.CMSsite2.com&lt;br /&gt;-------------AboutUs&lt;br /&gt;-------------OnlineShopping&lt;br /&gt;www.CMSsite3.com&lt;br /&gt;…&lt;br /&gt;&lt;br /&gt;Install a network loopback adapter and assign IP address from 192.168.2.1- 192.168.2.3&lt;br /&gt;&lt;br /&gt;In IIS Manger, create three web applications named and assign IP address as:&lt;br /&gt;www.CMSsite1.com  (192.168.2.1)&lt;br /&gt;www.CMSsite2.com  (192.168.2.2)&lt;br /&gt;www.CMSsite3.com  (192.168.2.3)&lt;br /&gt;&lt;br /&gt;Open %Winnt%\system32\drivers\etc\host with notepad and add following entries:&lt;br /&gt;192.168.2.1      www.CMSsite1.com &lt;br /&gt;192.168.2.2      www.CMSsite2.com &lt;br /&gt;192.168.2.3      www.CMSsite3.com &lt;br /&gt;&lt;br /&gt;So you may ask how will this related to HTTP host header mapping in IIS?&lt;br /&gt;Not a lot. IIS HTTP host header mapping is used to provide multiple-hosting. The HTTP host headers identify multiple virtual web sites that reside on one physical server and all sites shares same IP address.&lt;br /&gt;However, you need to configure the HTPP host headers on the IIS site if a single IP address is used for multiple CMS sites.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-109491030584116079?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/109491030584116079/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=109491030584116079' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/109491030584116079'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/109491030584116079'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2004/09/cms-sca-host-headers-mapping-vs-iis.html' title='CMS SCA Host Headers Mapping vs IIS HTTP Host Headers Mapping'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-109447743692566068</id><published>2004-09-06T14:06:00.000+01:00</published><updated>2006-11-01T12:35:35.411Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='not work'/><title type='text'>Pass another MCP exam</title><content type='html'>I passed the 70-320 MCP exam today, which is on Remoting, Serviced component, COM+, Windows services and XML web services. For the last 4 weeks or so, I totally enjoyed the pleasure of discovery. Ingo Rammer's &lt;a href="http://www.amazon.co.uk/exec/obidos/ASIN/1590590252/qid=1081325937"&gt;Advanced .NET Remoting&lt;/a&gt; is inspiring and fun to read. I got the book off my boss and gave him back with some coffee stains ;-).&lt;br /&gt;I reckon 70-320 is hardest one or at least it should be the hardest one to take, given the weight on each branch it tries cover. In a sense, Remoting and serviced component are the same hierarchy of .NET technology tack, like ASP.NET. However, 70-320 covers far more than that, which dilutes the depth it can accommodate in a two hours session. &lt;br /&gt;Serviced Component, the .Net version of COM+ is still the toughest part. I used Juval Lowy’s &lt;a href="http://www.amazon.co.uk/exec/obidos/ASIN/0596003471/"&gt;Programming .NET Components&lt;/a&gt; and Chapter 10 of his &lt;a href="http://www.amazon.co.uk/exec/obidos/ASIN/0596001037/%20"&gt; COM and .NET Component Services&lt;/a&gt; as introductory.&lt;br /&gt;If I were not heading for exam, I can probably explore more in-depth rather than board coverage. This is particular important to COM+ bit, which is hard to pick-up yet easy to drop-off.&lt;br /&gt;Now the challenge is: will I utilise these knowledge and skills and keep them sharp?&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-109447743692566068?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/109447743692566068/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=109447743692566068' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/109447743692566068'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/109447743692566068'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2004/09/pass-another-mcp-exam.html' title='Pass another MCP exam'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-109432806890562621</id><published>2004-09-04T21:01:00.000+01:00</published><updated>2006-11-01T12:40:05.453Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='.net'/><category scheme='http://www.blogger.com/atom/ns#' term='service component'/><title type='text'>Should I use SetAbort()/SetComplete() or DisableCommit()/EnableCommit()?</title><content type='html'>It was originally from a MCP vendor exercise question. I have it modified slightly:&lt;br /&gt;&lt;div id="div1" style="background-color: rgb(204, 204, 204);"&gt;&lt;br /&gt;You are creating a serviced component named UserManager. UserManager adds user&lt;br /&gt;accounts to multiple transactional data sources.&lt;br /&gt;The UserManager class includes the following code segment:&lt;br /&gt;&lt;span class="code"&gt;&lt;br /&gt;[Transaction(TransactionOption.Required)]&lt;br /&gt;[ObjectPooling(true, MinPoolSize=1, MaxPoolSize=50)]&lt;br /&gt;[JustInTimeActivation()]&lt;br /&gt;public class UserManager : ServicedComponent {&lt;br /&gt;public void AddUser(string TestKname, string TestKpassword)&lt;br /&gt;{&lt;br /&gt;// Code to add the user to data sources goes here.&lt;br /&gt;}&lt;br /&gt;}&lt;br /&gt;&lt;/span&gt;&lt;br /&gt;You must ensure that the AddUser method reliably saves the new user to either all data&lt;br /&gt;sources or no data sources. What should you do?&lt;br /&gt;A. To AddUser, add the following attribute:&lt;br /&gt;[AutoComplete()]&lt;br /&gt;B. To UserManager, add the following attribute:&lt;br /&gt;[JustInTimeActivation(false)]&lt;br /&gt;C. To the end of AddUser, add the following line of code:&lt;br /&gt;ContextUtil.EnableCommit();&lt;br /&gt;D. To the end of AddUser, add the following line of code:&lt;br /&gt;ContextUtil.SetComplete();&lt;br /&gt;E. To the end of AddUser, add the following line of code:&lt;br /&gt;ContextUtil.MyTransactionVote = true;&lt;br /&gt;&lt;/div&gt;&lt;br /&gt;&lt;br /&gt;IMHO, there are two issues need to be addressed here:&lt;br /&gt;1. Object activation and pooling. &lt;a href="http://www.dotnet247.com/247reference/msgs/49/246495.aspx"&gt;.NET 247 : object persistence across client method calls&lt;/a&gt; discusses this issue. Basically, the ‘done’ flag decide whether an object is ‘done’ and can be deactivated.&lt;br /&gt;2. MyTransactionVote or consistent flag.&lt;br /&gt;&lt;br /&gt;The SDK Doc says, ‘When MyTransactionVote is set to Commit, the COM+ consistent bit is set to true and the COM+ context votes to commit the transaction. If MyTransactionVote is set to Abort, the consistent bit is set to false and the COM+ context votes to abort the transaction.’&lt;br /&gt;&lt;br /&gt;And here is matrix of the four methods:&lt;br /&gt;METHOD---------------consistent---------------done&lt;br /&gt;SetComplete()------------true-----------------true&lt;br /&gt;SetAbort()---------------false----------------true&lt;br /&gt;EnableCommit()-----------true-----------------false&lt;br /&gt;DisableCommit()----------false----------------false&lt;br /&gt;&lt;br /&gt;The question is about when and how to do 1) ‘all or not’ transaction; 2) object activation and pooling.&lt;br /&gt;EnableCommit() cast a 'go' vote for transaction yet maintain the object as activated so C will be the best answer.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-109432806890562621?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/109432806890562621/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=109432806890562621' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/109432806890562621'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/109432806890562621'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2004/09/should-i-use-setabortsetcomplete-or.html' title='Should I use SetAbort()/SetComplete() or DisableCommit()/EnableCommit()?'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-109171979344725432</id><published>2004-08-05T16:29:00.000+01:00</published><updated>2006-11-01T12:40:25.025Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='not work'/><title type='text'>CV Crap</title><content type='html'>I heard this term from a friend who worked as a recruitment agent. The term is referring to those people put in all buzz words in their CV, such like C/C++/C#/JAVA/VB, UNIX/WINDOWS etc.&lt;br /&gt;Unfortunately, I am sliding to the edge of a CV crap. Our employer decided to abandon .NET technology for some period and asked all engineers to pick up a second skill set from existing system – which sound to me like pre-emptive notice of another round of ‘reorganisation’- anyway, I am doing Java J2EE migration now.&lt;br /&gt;That would not stop me on the journey to .NET though. I still plan to take the other four MCSD exams before end of the year- maybe right time when we will find out what our employer wants.&lt;br /&gt;I now read in the morning journey to office, then spend a little time on exercises before crack into Java work. Occasionally I advise people on middleware development which is on C/C++. I do some ASP .NET application in the evening at the moment.&lt;br /&gt;&lt;br /&gt;Til the end it is how you think not languages mattered.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-109171979344725432?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/109171979344725432/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=109171979344725432' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/109171979344725432'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/109171979344725432'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2004/08/cv-crap.html' title='CV Crap'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-109149022009445486</id><published>2004-08-03T00:43:00.000+01:00</published><updated>2006-11-01T12:40:51.443Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='asp.net'/><title type='text'>Asynchronous call for Web Forms</title><content type='html'>Call back function is useful in catch asynchronous result arrival event. It works fine on those known sockets/connection such like WIN FORM, Web Services. However, it is not applicable for Web form. There is simply no easy, reliable way for server to notify client browser.&lt;br /&gt;&lt;br /&gt;WaitOne, WaitAny and WaitAll provides a mechanism allowing a Web form to multi-task background processes and collect result after they have completed. Read this &lt;a href="http://searchvb.techtarget.com/vsnetTip/1,293823,sid8_gci800343_tax293033,00.html"&gt;Optimizing Web service calls from Web Forms&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;This pattern is not that helpful when comes to UI, however.&lt;br /&gt;Image there is a long run process, I want to display a progress bar one the call has been made. Then a few ten seconds later, I want to collect the result and update the UI accordingly- just show the progress bar if the result is not ready. You have to use script to refresh browser.&lt;br /&gt;&lt;br /&gt;(5/03/2005)Just found &lt;a href="http://dave.cornelson.net/commentview.aspx/f80a6286-a41a-4527-99de-2be9205d4aff"&gt;this discussion&lt;/a&gt; that suggests implementing System.Web.IHttpAsyncHandler interface in the page behind class which sloves the problem.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-109149022009445486?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='related' href='http://searchvb.techtarget.com/vsnetTip/1,293823,sid8_gci800343_tax293033,00.html' title='Asynchronous call for Web Forms'/><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/109149022009445486/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=109149022009445486' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/109149022009445486'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/109149022009445486'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2004/08/asynchronous-call-for-web-forms.html' title='Asynchronous call for Web Forms'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-109092258345612446</id><published>2004-07-27T11:01:00.000+01:00</published><updated>2006-11-01T12:41:12.219Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='service component'/><title type='text'>Remoting Basic</title><content type='html'>MarshalByRef executes remote method calls on the server side. Only ObjRef-networked object pointer is passed around. Client doesn't have the complied object, but the interface or base class to the object.&lt;br /&gt;&lt;br /&gt;ByValue  - class need to be serializable. Object is serialized to binary or string(xml) and transport between server/client. It then restored to a copy of the original object at the other end. Which means client and server both need the complied class prototype. State info is preserved.&lt;br /&gt;&lt;br /&gt;Basic Architecture&lt;br /&gt;At least three three assemblies are needed for a .net remoting project:&lt;br /&gt;1. Shared Assembly:  Client and server both need to have access to the same interface definition (MarshalByRef), serializable objects(ByValue)&lt;br /&gt;2. Server&lt;br /&gt;3. Client&lt;br /&gt;&lt;br /&gt;Implement remoting project: Life Cycle&lt;br /&gt;1. Implement SharedAssembly&lt;br /&gt;1.1 Define the remote interface&lt;br /&gt;1.2 Define data class that will be passed around in the shared&lt;br /&gt;&lt;br /&gt;2. Implement Server&lt;br /&gt;2.1 Implement the interface by Server.&lt;br /&gt;2.2 Create a new channel and register it to the remoting service.&lt;br /&gt;2.3 Register the server service as "RegisterWellKnownServiceType"&lt;br /&gt;&lt;br /&gt;3. Implement client&lt;br /&gt;3.1 Registering client channel&lt;br /&gt;3.2 create local proxt object to forward calls to server&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-109092258345612446?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/109092258345612446/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=109092258345612446' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/109092258345612446'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/109092258345612446'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2004/07/remoting-basic.html' title='Remoting Basic'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-108964359698027944</id><published>2004-07-12T15:17:00.000+01:00</published><updated>2006-11-01T12:41:21.943Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='not work'/><title type='text'>A dose of anti-depression</title><content type='html'>Having been feeling nothing exciting to do on the techie bits- well, in fact not many things to do at work at all for a while, I doubt I got the Clinic Depression after taking a 10 minutes quiz online*.&lt;br /&gt;&lt;br /&gt;Clinic Depression is not a work-avoidance excuse or can be taken lightly. As the reference material says, you need to take counselling and some pills for a really long time. It is a mood in that, you loss interests on everything and don’t want to get in with those even most fascinating things before. You tell yourself to ‘I need to put everything together’, but you just can’t’.&lt;br /&gt;&lt;br /&gt;Instead of loss in this hollow, I booked a Microsoft ASP.NET exam (70-315) bluntly. It costs about 100 pounds for about two hours. I decided to pay it myself instead of ask my boss to sign the bill- just to full load the pressure on myself.&lt;br /&gt;&lt;br /&gt;Thought I have done some ASP.NET for about a year so far, I never have a proper or well scheduled learning period before. Got three weeks to prepare for it at that time. At some points I start to think ‘should I re-schedule the exam?’ I didn’t.&lt;br /&gt;&lt;br /&gt;Instead, I told everyone in the team about it three days before the exam, so the pressure is at the explosive point. (Actually, it is quite silly to do that, not even leave a fail-back place.)&lt;br /&gt;&lt;br /&gt;I took the exam this morning.&lt;br /&gt;&lt;br /&gt;&lt;strong&gt;And I passed!&lt;/strong&gt; With a score 906 out of 1000. The pass mark is 700.&lt;br /&gt;&lt;br /&gt;It is really good news in any sense. I did learn a lot of new ASP.NET stuff, and lights shed on to those corners in normal developer’s lives will probably missed, such like deployment or security configuration. And I got out from the depression mood completely and feeling fully charged and in control now.&lt;br /&gt;&lt;br /&gt;I wouldn’t say it is the end/top of the ASP.NET skills I will have. It wouldn’t stop there. I take it as a bench mark which means I can progress further.&lt;br /&gt;&lt;br /&gt;And overall, I just proofed MCSD exams are most effective anti-depression drugs money can buy.&lt;br /&gt;&lt;br /&gt;&lt;em&gt;*As Nick pointed out, the online quiz is targeting female audience. I reckon it should work for both.&lt;/em&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-108964359698027944?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/108964359698027944/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=108964359698027944' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/108964359698027944'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/108964359698027944'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2004/07/dose-of-anti-depression.html' title='A dose of anti-depression'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-108956933412258327</id><published>2004-07-11T19:08:00.000+01:00</published><updated>2006-11-01T12:41:35.286Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='asp.net'/><title type='text'>Debug JavaScript in ASP.NET Apps</title><content type='html'>&lt;a href="http://devcenter.infragistics.com/Articles/ArticleTemplate.Aspx?ArticleID=2183"&gt;Debug JavaScript in ASP.NET Apps&lt;/a&gt;tells how to debug client script:&lt;br /&gt;Assuming we 'inject' following code snippets to create client side script&lt;br /&gt;&lt;div id="div1" class="Code"&gt;&lt;br /&gt;&lt;!-- test.aspx --&gt;&lt;br /&gt;  &amp;lt;script language="javascript"&amp;gt;&lt;br /&gt;   function DoSomething()&lt;br /&gt;   {&lt;br /&gt;    alert("Hello");&lt;br /&gt;   }&lt;br /&gt;  &amp;lt;/script&amp;gt;&lt;br /&gt;&lt;br /&gt;//in the code behind test.aspx.cs&lt;br /&gt;  private void Page_Load(object sender, System.EventArgs e)&lt;br /&gt;  {&lt;br /&gt;   btnClick.Attributes.Add("OnClick","JavaScript:return DoSomething();");&lt;br /&gt;  }&lt;br /&gt;&lt;/div&gt;&lt;br /&gt;&lt;br /&gt;We can set break point at DoSomething() by:&lt;br /&gt;1) Open Internet Explorer, choose Tools | Internet Options. Click the Advanced tab and find Disable script debugging. Clear the checkbox.&lt;br /&gt;2) In VS.NET IDE, press F5 to launch process in debug mode.&lt;br /&gt;3) Navigate to the web page contains the script- test.aspx&lt;br /&gt;4) Open 'Running Ducuments' window on IDE by selecting Debug | Windows | Running Documents, Running Ducuments Window launch and give a tree list of all document;&lt;br /&gt;5) Double click test.aspx to load it into IDE browser window.&lt;br /&gt;6) Place break point, monitoring variables as usual.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-108956933412258327?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='related' href='http://devcenter.infragistics.com/Articles/ArticleTemplate.Aspx?ArticleID=2183' title='Debug JavaScript in ASP.NET Apps'/><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/108956933412258327/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=108956933412258327' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/108956933412258327'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/108956933412258327'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2004/07/debug-javascript-in-aspnet-apps.html' title='Debug JavaScript in ASP.NET Apps'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-108860256237161619</id><published>2004-06-30T14:36:00.000+01:00</published><updated>2006-11-01T12:41:54.553Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='asp.net'/><title type='text'>Server Side ViewState</title><content type='html'>&lt;a href="http://authors.aspalliance.com/robertb/articles.aspx?articleId=2"&gt;Server Side ViewState&lt;/a&gt;: I will have a closer look at this later&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-108860256237161619?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='related' href='http://authors.aspalliance.com/robertb/articles.aspx?articleId=2' title='Server Side ViewState'/><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/108860256237161619/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=108860256237161619' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/108860256237161619'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/108860256237161619'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2004/06/server-side-viewstate.html' title='Server Side ViewState'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-108852784273271638</id><published>2004-06-29T17:50:00.000+01:00</published><updated>2006-11-01T12:42:15.964Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='.net'/><title type='text'>Documenting Exceptional Developers</title><content type='html'>&lt;a href="http://www.eggheadcafe.com/articles/20030127.asp"&gt;Documenting Exceptional Developers&lt;/a&gt; seemed gives some pragamatic arguements on use try-catch wisely.&lt;br /&gt;&lt;br /&gt;If Matt insists to make 'user login failure' kind of things as exceptions, I will show him this article and call him 'exceptional coder' ;-)&lt;br /&gt;&lt;br /&gt;Also from Peter Bromberg, &lt;a href="http://www.eggheadcafe.com/articles/20030816.asp"&gt;Build a Really Useful ASP.NET Exception Engine&lt;/a&gt; is more interesting to try out.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-108852784273271638?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='related' href='http://www.eggheadcafe.com/articles/20030127.asp' title='Documenting Exceptional Developers'/><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/108852784273271638/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=108852784273271638' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/108852784273271638'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/108852784273271638'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2004/06/documenting-exceptional-developers.html' title='Documenting Exceptional Developers'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-108852612681995067</id><published>2004-06-29T17:22:00.000+01:00</published><updated>2006-11-01T12:42:54.339Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='asp.net'/><title type='text'>OnError and [Page]_Error</title><content type='html'>Aspx Page have two event methods: &lt;strong&gt;[Page]_Error &lt;/strong&gt;and &lt;strong&gt;OnError&lt;/strong&gt;. They are different. OnError hands control to a private &lt;strong&gt;HandleError &lt;/strong&gt;method. &lt;strong&gt;HandleError &lt;/strong&gt;checks whether web.config:&lt;strong&gt;customErrors &lt;/strong&gt;is turned on and redirects request accordingly.&lt;br /&gt;The base implementation on &lt;strong&gt;OnError&lt;/strong&gt;:  checks whether tracing is turned on and adds its own bit about the exception just raised. The main reason to override OnError is to replace this behavior with your own implementation. There is no good reason to put other code there. If &amp;lt;customErrors&amp;gt; turned on, code in OnError will fire first then redirect request to customized error page. In this case code in &lt;strong&gt;Page_Error &lt;/strong&gt;will not fire, as OnError fires first.&lt;br /&gt;To do error-handling at the Page level, use Page_Error.&lt;br /&gt;&lt;br /&gt;Experiment&lt;br /&gt;Create an aspx page &lt;span id="span2906041" css="CodeSnippet"&gt;ManMadeError &lt;/span&gt;with both event handling methods:&lt;br /&gt;&lt;div id="div290620041" class="Code"&gt;&lt;br /&gt;  private void ManMadeError_Error(object sender, System.EventArgs e)&lt;br /&gt;  {&lt;br /&gt;   Exception ex = Server.GetLastError();&lt;br /&gt;   //   System.Diagnostics.Trace.WriteLine(ex.ToString(), "Error");&lt;br /&gt;   if (Trace.IsEnabled)&lt;br /&gt;    Response.Write("Trace on");&lt;br /&gt;  &lt;br /&gt;   Trace.Warn("Error",ex.ToString());&lt;br /&gt;   Session["Error"] = ex;&lt;br /&gt;   Server.ClearError();&lt;br /&gt;   Server.Transfer("500.aspx");&lt;br /&gt;  }&lt;br /&gt;  protected override void OnError(EventArgs e)&lt;br /&gt;  {&lt;br /&gt;   Response.Write("&amp;lt;h1&amp;gt; We have a problem &amp;lt;/H1&amp;gt;");&lt;br /&gt;  }&lt;br /&gt;&lt;/div&gt;&lt;br /&gt;in Web.config, we have&lt;br /&gt;&lt;div id="div2906042" class="Code"&gt;&lt;br /&gt;   &amp;lt;customErrors mode="On" defaultRedirect="./Errors/500.aspx" &amp;gt;&lt;br /&gt;  &amp;lt;error statusCode="401" redirect="./Chp8Security/Authen_2.aspx" /&amp;gt;&lt;br /&gt;  &amp;lt;error statusCode="500" redirect="./Errors/500.aspx" /&amp;gt;&lt;br /&gt;  &amp;lt;error statusCode="404" redirect="./Errors/404.aspx" /&amp;gt;&lt;br /&gt; &amp;lt;/customErrors&amp;gt;&lt;br /&gt;&lt;/div&gt;&lt;br /&gt;Fires the exception, and watch the implantation in ManMadeError_Error is ignored entirely.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-108852612681995067?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/108852612681995067/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=108852612681995067' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/108852612681995067'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/108852612681995067'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2004/06/onerror-and-pageerror.html' title='OnError and [Page]_Error'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-108850846106117975</id><published>2004-06-29T12:27:00.000+01:00</published><updated>2006-11-01T12:43:32.680Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='asp.net'/><title type='text'>Customised application error page</title><content type='html'>We can specify error pages to intercept HTTP errors using Web.config file.&lt;br /&gt;To display a specific error handling page for HTTP status code such like 404(NotFound), 500(InternalServerError), 401(Unauthorized)etc we can add the following element to the web app’s web.config file:&lt;br /&gt;&lt;div id="div2906043" class="Code"&gt;&lt;br /&gt;   &amp;lt;customErrors mode="On" defaultRedirect="./Errors/wehaveaproblem.aspx" &amp;gt;&lt;br /&gt;  &amp;lt;error statusCode="401" redirect="login.aspx" /&amp;gt;&lt;br /&gt;  &amp;lt;error statusCode="500" redirect="./Errors/wehaveaproblem.aspx " /&amp;gt;&lt;br /&gt;  &amp;lt;!-- redirect to the 404 page only valid for URLs that end with aspx.&lt;br /&gt;  Need to config IIS to take other page types --&amp;gt;&lt;br /&gt;  &amp;lt;error statusCode="404" redirect="./Errors/404.aspx" /&amp;gt;&lt;br /&gt; &amp;lt;/customErrors&amp;gt;&lt;br /&gt;&lt;/div&gt;&lt;br /&gt;To the 404 error, by default it only works for .aspx and .asp pages. Requesting pages like .htm or .html will still fail back to default MS 404 page. To enable our IIS App handling .htm, you need to map .htm/.html  request so it could be handled by aspnet_isapi.dll.&lt;br /&gt;Open IIS manager, click &lt;span id="span290620043" class="CodeSnippet"&gt;‘(Application) configuration…’&lt;/span&gt; and in &lt;span id="span290620044" class="CodeSinppet"&gt;‘(‘Application mapping’&lt;/span&gt; tab, add htm extension. Map it to &lt;span id="span290620045" class="CodeSinppet"&gt;‘((install_drive) \WINNT\Microsoft.NET\Framework\(version)\aspnet_isapi.dll&lt;/span&gt;.&lt;br /&gt;&lt;br /&gt;Once this is done, you may notice the app is giving back a 500 at default home page (http://www.mySite.com/), if you use a default.aspx page. This is because the default document retrieval order is set to default.htm-default.asp-iistart.asp-default.aspx. Add a dummy default.htm page to redirect the request to default.aspx as following(need client side to enable scripting):&lt;br /&gt;&lt;div id="”div2606045”" class="Code"&gt;&lt;br /&gt; &amp;lt;script language=javascript&amp;gt;&lt;br /&gt;  window.navigate("default.aspx")&lt;br /&gt; &amp;lt;/script&amp;gt;&lt;br /&gt;&lt;/div&gt;&lt;br /&gt;The other way to do display customised error page is by configuring IIS in Custom Errors Setting.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-108850846106117975?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/108850846106117975/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=108850846106117975' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/108850846106117975'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/108850846106117975'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2004/06/customised-application-error-page.html' title='Customised application error page'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-108841851901837495</id><published>2004-06-28T11:28:00.000+01:00</published><updated>2006-11-01T12:44:07.297Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='service component'/><title type='text'>ASMX serialization vs. binary serialization with remoting</title><content type='html'>Remoting is useful for crossing app domains, but not for crossing machine boundaries. Check&lt;br /&gt;&lt;a href="http://weblogs.asp.net/shawnmor/archive/2004/05/27/143209.aspx"&gt;this&lt;/a&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-108841851901837495?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='related' href='http://weblogs.asp.net/shawnmor/archive/2004/05/27/143209.aspx' title='ASMX serialization vs. binary serialization with remoting'/><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/108841851901837495/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=108841851901837495' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/108841851901837495'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/108841851901837495'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2004/06/asmx-serialization-vs-binary.html' title='ASMX serialization vs. binary serialization with remoting'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-108811671362742467</id><published>2004-06-24T23:38:00.000+01:00</published><updated>2006-11-01T12:44:38.302Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='asp.net'/><title type='text'>IsAuthenticated?</title><content type='html'>Issue: Form Based authentication, authenticated state cannot be kept between pages navigation in a web application.&lt;br /&gt;The sample web app has been tested on a w2k svr which is a domain member and worked fine.&lt;br /&gt;Moving to a stand alone w2k- my home PC, it failed. Trace file indicates the credentials has been authenticated (&lt;em&gt;FormsAuthentication.Authenticate&lt;/em&gt;). On page redirection (&lt;em&gt;FormsAuthentication.RedirectFromLoginPage(txtUserName.Text, false);&lt;/em&gt;), the authenticated state lost.&lt;br /&gt;Having run the IIS authentication diagnostic tool (http://www.iisfaq.net/), I found it point to the fact the IIS Web Server needs to be a domain member.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-108811671362742467?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/108811671362742467/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=108811671362742467' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/108811671362742467'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/108811671362742467'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2004/06/isauthenticated.html' title='IsAuthenticated?'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6082242.post-109103514469036543</id><published>2004-05-28T18:16:00.000+01:00</published><updated>2006-11-01T12:45:14.916Z</updated><category scheme='http://www.blogger.com/atom/ns#' term='asp.net'/><title type='text'>403 error when accessing a CMS site for the first time</title><content type='html'>It is worth to check SCA and set 'Map Channel Names to Host Header Names' has set to 'YES' first. In my case, I configurate IIS to use host header mapping and hence this also need to be set accordingly&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6082242-109103514469036543?l=jingyeluo.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://jingyeluo.blogspot.com/feeds/109103514469036543/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=6082242&amp;postID=109103514469036543' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/109103514469036543'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6082242/posts/default/109103514469036543'/><link rel='alternate' type='text/html' href='http://jingyeluo.blogspot.com/2004/05/403-error-when-accessing-cms-site-for.html' title='403 error when accessing a CMS site for the first time'/><author><name>Jingye</name><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='24' height='32' src='http://www.e-jingyeluo.com/general_non_postnuke/images/Jingye_mob.jpg'/></author><thr:total>0</thr:total></entry></feed>
