<?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-31707900</id><updated>2011-12-10T21:46:54.470-05:00</updated><category term='Automated'/><category term='Software Development Process'/><category term='Building'/><category term='Agile'/><category term='Software Process Tracking'/><category term='Source Control'/><category term='Software Process Improvement'/><category term='Code Working'/><category term='Review'/><category term='Software Process'/><category term='Algorithms'/><category term='Application'/><category term='Testing'/><title type='text'>Technopinions</title><subtitle type='html'>Software process and the ilk</subtitle><link rel='http://schemas.google.com/g/2005#feed' type='application/atom+xml' href='http://software-process.blogspot.com/feeds/posts/default'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/31707900/posts/default?max-results=100'/><link rel='alternate' type='text/html' href='http://software-process.blogspot.com/'/><link rel='hub' href='http://pubsubhubbub.appspot.com/'/><author><name>Carl Cox</name><uri>http://www.blogger.com/profile/11479857805045070539</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><generator version='7.00' uri='http://www.blogger.com'>Blogger</generator><openSearch:totalResults>9</openSearch:totalResults><openSearch:startIndex>1</openSearch:startIndex><openSearch:itemsPerPage>100</openSearch:itemsPerPage><entry><id>tag:blogger.com,1999:blog-31707900.post-8513655497925760920</id><published>2008-09-15T14:13:00.005-05:00</published><updated>2008-09-15T14:17:30.060-05:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Application'/><category scheme='http://www.blogger.com/atom/ns#' term='Testing'/><category scheme='http://www.blogger.com/atom/ns#' term='Automated'/><title type='text'>File2Port</title><content type='html'>I have uploaded my mini app, &lt;a href="http://www.prism.gatech.edu/~cc263/software/File2Port.exe"&gt;File2Port&lt;/a&gt; so that anyone can use it.  The purpose is to test tcp clients and servers by providing a dummy endpoint to connect.  It can send text from a file to a port and receive information from a port to place in a file.  Currently this gets updated as I find it useful, but if you would like something added, let me know in comments and I will see what I can do.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/31707900-8513655497925760920?l=software-process.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='related' href='http://www.prism.gatech.edu/~cc263/software/' title='File2Port'/><link rel='replies' type='application/atom+xml' href='http://software-process.blogspot.com/feeds/8513655497925760920/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=31707900&amp;postID=8513655497925760920&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/31707900/posts/default/8513655497925760920'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/31707900/posts/default/8513655497925760920'/><link rel='alternate' type='text/html' href='http://software-process.blogspot.com/2008/09/file2port.html' title='File2Port'/><author><name>Carl Cox</name><uri>http://www.blogger.com/profile/11479857805045070539</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-31707900.post-2131946773501487865</id><published>2007-03-01T20:56:00.001-05:00</published><updated>2007-03-01T21:52:17.509-05:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Code Working'/><category scheme='http://www.blogger.com/atom/ns#' term='Source Control'/><title type='text'>Source Repository Layout</title><content type='html'>I spent a pleasant amount of time today looking into whether I want to replace my personal CVS version control with SVN.  Subversion, you may know, is the much touted Open Source Solution to Version Control, burying CVS in features and so forth.  This led to research about the truths of the matter (SVN looks good enough for me to give it a try - I do love my TortoiseCVS, but I'll try out TortoiseSVN), which led to the "standard" repository layout.&lt;br /&gt;&lt;br /&gt;Now, I've been developing for long enough to recognize a "standard" repository by now, and I've seen enough to know that I haven't seen a standard.  Done some work to improve the repositories I work with, both personally and on a team, but I hadn't given it much thought beyond that.  Well, here it is:&lt;br /&gt;&lt;br /&gt;/project&lt;br /&gt;/project/trunk&lt;br /&gt;/project/branches&lt;br /&gt;/project/tags&lt;br /&gt;&lt;br /&gt;What were you expecting, magic?&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight:bold;"&gt;Failed Similes&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;Basically, this layout addresses life-cycles of projects.  When a baby project is just being grown, of course we want protect it as much as possible.  This means using source control.  When something bad happens to the baby, we can just back up and restore the healthy child.  If only real life were so simple!  &lt;br /&gt;&lt;br /&gt;When the baby becomes an adult, we typically want to release him into the wild.  This "release" is something we want to hold on to.  After all, people might come back and say the kid has some problem, like 4 fingers when he should have 5.  We want to be able to fix those problems.  On the other hand, we &lt;i&gt;also&lt;/i&gt; want the kid to grow more, do more things.  Basically, we have a problem.  In real life, the kid can't leave and stay at the same time.  Fortunately, software is not a kid, and the analogy holds no water.  Like a prepositional phrase, it is out of here.&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight:bold;"&gt;Like Elephants and Trees&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;What we want is to have two semi-related developments of the code: a &lt;i&gt;release&lt;/i&gt; development, where we can address problems that users find and turn around with a patched version quickly, and an &lt;i&gt;experimental&lt;/i&gt; version where we can try new things, throw out old things, and generally make a mess without worrying about John Q. Public.  &lt;br /&gt;&lt;br /&gt;Wait a second.  The experimental version is kind of what the program was like before it was released, right?  It didn't matter if this feature or that change broke everything, because Mr. Public hadn't seen anything yet.  This experimental, playful (if you will) code state provides the core of everything else we wind up doing.  It's where we say "what if" and see what happens.  When good things happen, we turn it into a release.  When bad things happen, we restore previous versions and move on.  Since everything else stems from this, we'll call it the "trunk".&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight:bold;"&gt;Of Streams and Rivulets&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;Release development typically results in a series of numbers.  1.0.  1.1.  1.2.  2.0.  and so on.  The 1.0 1.1 1.2 series is frequently a series of small changes.  We found some bugs in the 1.0 code, so we fixed it and called that 1.1.  We added a feature to that and released it, calling it 1.2  This is similar to the trunk, because we're taking a root and building on it.  But it's different, too.  We don't necessarily want these changes in the trunk, for one thing.  (Of course, we might.  That's what merging is for.)  For another thing, it's not as playful.  We need to have more certainty that we didn't break any of Mr. Public's expectations, no new bugs.  &lt;br /&gt;&lt;br /&gt;These are our "branches".  By keeping them separate from the trunk, we can freely develop both at any time.  We can even branch branches.  Years later, when our trunk has wandered so far from our branches that we'd never know they were the same, we can still return to those branches to maintain and enhance them.  &lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight:bold;"&gt;Frozen in Time&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;So far we have lots of growing things, quite the populous plant.  Theoretically, we can get to every version of the code in the trunk and all the branches, and they can all grow independently of each other.  But there's the practical side, too.  We want to get to 1.1.  Here we leave our forest discussion and invent a "tag".&lt;br /&gt;&lt;br /&gt;A tag is a moment in code history.  In development, there is a time when we say to each other: "Now.  Now is when we release this code upon the world.  Now is when it is ready."  We nod knowingly.  This is a big moment, and we may need to get back to it later.  Here we tag the branch that is ready; we name it for the great out side; we call it "1.0".  And we tag it, "1.0".&lt;br /&gt;&lt;br /&gt;Later, we can come back to 1.0, fix those bugs, add those features, then tag and release "1.1".  Tags are our ticket back to the past.  Those four letters contain a flux capacitor, and we can see Doc's smile.&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight:bold;"&gt;Are Magic&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;Now we know why the layout is standard.  Well, it's not "standard", but it certainly seems to make sense.  We know where our trunk development goes, we know where our branch development goes, and we can see where our tags go.  Of course, the exact folder names and placement aren't quite as important as the ideas.  We want to make our jobs as easy as possible; keeping these three concepts separate and clear does just that.  So, when we see the layout:&lt;br /&gt;&lt;br /&gt;/project&lt;br /&gt;/project/trunk&lt;br /&gt;/project/branches&lt;br /&gt;/project/tags&lt;br /&gt;&lt;br /&gt;we &lt;i&gt;are&lt;/i&gt; seeing a little bit of magic.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/31707900-2131946773501487865?l=software-process.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://software-process.blogspot.com/feeds/2131946773501487865/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=31707900&amp;postID=2131946773501487865&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/31707900/posts/default/2131946773501487865'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/31707900/posts/default/2131946773501487865'/><link rel='alternate' type='text/html' href='http://software-process.blogspot.com/2007/03/source-repository-layout.html' title='Source Repository Layout'/><author><name>Carl Cox</name><uri>http://www.blogger.com/profile/11479857805045070539</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-31707900.post-4755412405767969052</id><published>2007-01-23T14:47:00.000-05:00</published><updated>2007-01-23T14:57:30.867-05:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Software Development Process'/><category scheme='http://www.blogger.com/atom/ns#' term='Review'/><category scheme='http://www.blogger.com/atom/ns#' term='Software Process Improvement'/><category scheme='http://www.blogger.com/atom/ns#' term='Software Process'/><category scheme='http://www.blogger.com/atom/ns#' term='Agile'/><title type='text'>Book Review: Balancing Agility and Discipline</title><content type='html'>Recently I finished reading &lt;a href="http://www.amazon.com/Balancing-Agility-Discipline-Guide-Perplexed/dp/0321186125"&gt;Balancing Agility and Discipline: A Guide for the Perplexed&lt;/a&gt; by Barry Boehm and Richard Turner.  It's the first book I've read that attempts to find a logical middle ground among all the hollering from Agile Zealots, CMM Traditionalists, and the Process Atheists.  It's aimed at those interested in their development team, whether developer, task leader, or manager, and describes some of the pros and cons of Agile methods (such as XP and Scrum) and more traditional "Discipline" methods (such as RUP and TSP/PSP).  Additionally, the book takes a reasonable stab at how to roll our own process.&lt;br /&gt;&lt;br /&gt;Is it useful?  Yes, but under certain caveats.&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight:bold;"&gt;McProcess: Prepared for Convenience&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;The project must be willing to accept that growing their own process will be measurably better than using a "prepackaged" process.  In my experience, this is not the case.  Most of the time, people want the packaged solutions: all the rules and procedures are defined, it is easy to see how much of the process is really being used, and they are easy to talk about (they have a &lt;i&gt;name&lt;/i&gt; .  Like a box dinner, organizations just want to stick a process in and go.  In contrast, preparing their own process implies work - deciding on individual rules and procedures, trying to determine how much can and should be used, probably getting input from all levels in the organization.  There's not even a name to attach to the process.&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight:bold;"&gt;Employee Diet&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;The project must have available people experiences in many different processes, and be able to judge how this or that practice will be taken by the engineers who will use them.  This will help decide how much training is required to implement various practices.  For example, if we want to start using pair programming, but no one in our company has ever done it, we may have to devote real resources into getting that practice started and accepted.  It will be much worse if we &lt;i&gt;have&lt;/i&gt; engineers who are experiences in pair programming, but hate it.&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight:bold;"&gt;&lt;br /&gt;Chapter breakdown&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;Chapter 1 introduces the problem domain: software is hard, people don't understand how to make it.  Disciplined methods, ala waterfall, originally proposed to solve problems by taking techniques from classic engineering.  Unfortunately, that didn't work.  Agile methods, developed in response to "failings" in Disciplined methods, took a less regimented approach to development, but, alas, also failed to make everyone happy.  Clearly, there must be another way.&lt;br /&gt;&lt;br /&gt;Chapter 2 gets into the mud a little and talks specifics.  Both Agile methods and Disciplined methods have a "Home Ground", or characteristics that help the process succeed.  These characteristics include personnel counts and skills, requirements stability, development culture, and ultimate project failure costs (lives, money, comforts).&lt;br /&gt;&lt;br /&gt;Chapter 3 describes normal and "crisis" days for both Agile and Disciplined methods, from arrival to departure of the development and management teams.  We get to see some of the style of interactions between team members for both types of methods.&lt;br /&gt;&lt;br /&gt;Chapter 4 takes case studies for Agile and Disciplined processes.  It points out where the processes failed and how these failures might be handled.&lt;br /&gt;&lt;br /&gt;Chapter 5 proposes a method to roll our own process.  Examining the risk of using one approach versus the risk of &lt;i&gt;not&lt;/i&gt; using it can be very informative. We can rate our projects on the "Home Ground" scales and see whether they call solidly into Agile or Disciplined methods, and take steps accordingly.  Most importantly, the book acknowledges we can pick and choose what pieces work for us.  We can build a process from other processes, custom tailored for our project.&lt;br /&gt;&lt;br /&gt;Finally, chapter 6 summarizes the book.  Neither Agile methods nor Disciplined methods will magically solve problems; developers and management still has to use some thought to decide what process styles they should adopt.  It seems to be better to make our own process from process pieces rather than take a process and trim it down.&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight:bold;"&gt;Obey your Thirst&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;Ultimately, I think this technique best benefits the rare project that is interested in improving their process, but has noticed that nothing really seems to be working.  The book itself has much broader range of use - any project team just getting underway will find a set of considerations in the portions of the book about "home ground", and it is certainly refreshing to read about process, agility, and iterative development without any resorting to fat-jokes.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/31707900-4755412405767969052?l=software-process.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://software-process.blogspot.com/feeds/4755412405767969052/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=31707900&amp;postID=4755412405767969052&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/31707900/posts/default/4755412405767969052'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/31707900/posts/default/4755412405767969052'/><link rel='alternate' type='text/html' href='http://software-process.blogspot.com/2007/01/book-review-balancing-agility-and.html' title='Book Review: Balancing Agility and Discipline'/><author><name>Carl Cox</name><uri>http://www.blogger.com/profile/11479857805045070539</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-31707900.post-7032132278645492899</id><published>2006-12-16T19:38:00.000-05:00</published><updated>2006-12-16T19:51:19.675-05:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Testing'/><category scheme='http://www.blogger.com/atom/ns#' term='Automated'/><category scheme='http://www.blogger.com/atom/ns#' term='Software Process'/><title type='text'>How I Leared to Stop PrintFing and Love Testing</title><content type='html'>&lt;span style="font-weight: bold;"&gt;Output Woes&lt;/span&gt;&lt;br /&gt;Back when I was a young buck cutting my teeth on silicon and spare cycles, I thought testing consisted of clever, or at least abundant, use of printing to console.  Such debugging has the advantage only of being easy to implement.  Test maintenance, relevance, repeatability, automatic checking: all these things were rumors, mythical weapons akin to Excalibur or a Vorpal Blade.  Since then, I have learned of the simplicity of breakpoints, the grace of call stacks, the depth of profilers, and, more than anything, the breathtaking wonder of Automated Tests.  Lo, and suddenly the mythical became the real, and gruesome beasts were slain.&lt;br /&gt;&lt;br /&gt;Back to my young buck days.  Many times I would write some code, test and debug it, and everything seemed beautiful.  I would test inline, printing variables, conditions, paths, and I was good.  My tests would even self proclaim their results: "Testing megasort: SUCCESS!" or "Testman saith: ABJECT FAILURE!"  Certain of my overwhelming tests, I would blot out the test code so to keep my final source pristine and move on.  Later I might notice a small change that needed to be made. Then, the day before (or worse, the day after) a deadline, I noticed that everything was broken.  The small change had, of course, affected something I hadn't thought about, something I had had a test for, but had stopped running and removed from the system.&lt;br /&gt;&lt;br /&gt;"No problem" I said in my sophomoric exuberance.  The next time, I didn't blot the code out.  I surrounded it with the ever imaginative "if(DEBUG)" statement.  Define DEBUG once for the whole system, and now I could test everything.  Of course, I still had to inspect everything, and the tests remained in my code...&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;Automated Vigor&lt;/span&gt; &lt;br /&gt;Thousands of iterations later I might have come up with Automated Tests.  I didn't, of course; people much wiser than me forged this weapon, but I gained the benefit.&lt;br /&gt;&lt;br /&gt;An Automated Test is a test that's run (gasp) automatically, usually at build time.  Automated Test frameworks abstract tests away from the code, so we can keep our code sharp and unblemished from the smelting fires of test code.  The tests report to the frameworks, rather than to standard out or an error file, and the framework, not the human, does the checking.  The framework only tells us when something goes wrong.  Since the tests are always run, we get notified when any tested code breaks, no matter the age.  They are a powerful tool of our craft.&lt;br /&gt;&lt;br /&gt;I began using Automated Tests when I took over the build process for a medium-sized java program.  Whenever the build broke, I needed to show the developer exactly how it broke.  This is when I discovered how often the same bug would pop up over and over.  I would show a developer his error, and the next week, it would reappear.  After introduced Automated Tests (in the form of JUnit) into the code, my life started easing up.  I no longer had to recreate a test over and over for the same bug - I could simply point to the test.  Then we integrated Automated Tests into our IDE, and things really started looking up.  Slowly the development team started running the tests before checking in code, and gradually our productivity increased, our code was cleaner, our bugs fewer.&lt;br /&gt;&lt;br /&gt;Automated tests are really just another extension of a Refactoring mindset: if something is worth coding multiple times, it's only worth coding once.  If we're going to do it several times, we're better off just doing it once and calling it several times.&lt;br /&gt;&lt;br /&gt;Of course, there are dark sides to anything.  Automated Tests are code, and code must be maintained.  It's possible to spend all our time writing tests that are repeated, or unnecessary.  Typically Automated Tests are not deliverable, which might throw off statistics for line-accountants.  Occasionally an ill-conceived test can send developers scampering off after ghost-bugs.  However, treated with respect they deserve, Automated Tests can help us slaughter bugs and guard against our tendency to resurrect them.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/31707900-7032132278645492899?l=software-process.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://software-process.blogspot.com/feeds/7032132278645492899/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=31707900&amp;postID=7032132278645492899&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/31707900/posts/default/7032132278645492899'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/31707900/posts/default/7032132278645492899'/><link rel='alternate' type='text/html' href='http://software-process.blogspot.com/2006/12/how-i-leared-to-stop-printfing-and-love.html' title='How I Leared to Stop PrintFing and Love Testing'/><author><name>Carl Cox</name><uri>http://www.blogger.com/profile/11479857805045070539</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-31707900.post-115998365829292050</id><published>2006-10-04T12:34:00.000-05:00</published><updated>2007-03-01T21:54:00.087-05:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Automated'/><category scheme='http://www.blogger.com/atom/ns#' term='Software Process'/><category scheme='http://www.blogger.com/atom/ns#' term='Building'/><title type='text'>Building Ideals</title><content type='html'>One of the failing points of the classic Waterfall Software Development Process is the separation of implementation and testing.  Many processes since have tried to overcome the obvious limitations imposed: the easiest of these by far is Frequent Builds, and the most useful of these is Automated Tests.  Bold claims! &lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;Frequent Builds&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;We know building our code ensures that everything still compiles; it's like saying the sun makes light, or traffic today will crawl.  But as our development effort grows, this seemingly obvious check becomes more important.  It pays, then, to make sure the check is happening often, and more, to make sure it's happening right.  Luckily, or providentially, we have more and more sophisticated auto-build tools, such as Ant, Nant, Visual Build, and so on, which take the pain of auto-building away.  Combined with simple scheduling, Frequent Builds are almost trivial.  Build once a week, once a day, once an hour.  Take your pick.&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;Automated Tests&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;Automated Tests add a whole new level of power to us.  Every time the build runs, run your tests; then for every test you write, that's one case you never have to worry about again.  We won't talk now about Zen and the art of writing automated tests, we'll pretend we all already know when and how to do that rigorously.  When we talk about building, we should be including our automated tests as well.  If a build doesn't pass its test, it didn't build correctly.&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;What does it all &lt;/span&gt;&lt;span style="font-style: italic; font-weight: bold;"&gt;mean?&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;But, even assuming everything we've said to this point is perfectly accurate and true, there are still simple questions left unanswered.  What's the &lt;span style="font-weight: bold;"&gt;best way&lt;/span&gt; to build?  How often &lt;span style="font-weight: bold;"&gt;should&lt;/span&gt; we build?  What does a build consist of, anyway?&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;First thing's last!&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;Builds should include everything needed for the program to run.  This including source code (of course), libraries, image files, and anything else needed while the program runs.  This does &lt;span style="font-weight: bold;"&gt;not&lt;/span&gt; include extra documentation, readme files, or pictures of Chichi, the dancing skeleton.&lt;br /&gt;&lt;br /&gt;Frequency of builds is a touchy subject.  I have been ostracized by bug-eyed zealots for suggesting that builds could happen more than once a day.  I have bemoaned weekly progress emails.  I haven't heard of wars being fought over the subject, but I'm sure minor skirmishes have.  When it comes down to it, you want your source tree to always successfully build; if processor time was nothing, we'd build whenever the source tree was updated (commit, checkin, whatever).  Of course, we can't do that... yet... so we need to content ourselves with something somewhat less ambitious.  For active development projects, building twice a day is probably sufficient.  For any project under even mild development, builds should happen at least once a day; there's no reason for less.&lt;br /&gt;&lt;br /&gt;Now, for the Great Act of Building, itself.  What should this ritual consist of?&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;Start Fresh&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;We want this build, and all builds, to be a perfect representation of the products being built.  We don't want old, mildewed code to spoil our pristine masterpiece.  Therefore, we always need to ensure we're building from the latest, greatest stuff; make sure every old thing is cleaned up - everything compiled previously and everything previously retrieved from source control.&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;Trust and Accountability&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;Removing all previously built components is well understood.  Mixed code components tend to make for weird errors.  But remove everything previously retrieved from source control?  It really depends on how much we trust our source control mechanisms.  If we know that SourceSafe is always going to correctly synchronize our local build, we wouldn't worry about this.  Too many things can go wrong - software bugs in source control, network failures, power failures.  We need to trust that when we start building, everything we have is brand new, and nothing slipped through the wires.  This way, if a build breaks in some way, we know it's not related to retrieving the source, just as we know it's not from building the source.&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;Avoid Conflicts&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;When we do get the source, we want to make sure everything we're getting is on the same footing.  We don't want to start synchronizing and have someone else check in code in the middle, such that we have half of that person's updates.  Ideally, of course, source control would deal with this problem, too.  Again, we can't take the risk of it being wrong.  Avoid these kinds of conflicts by labeling the entire source we're about to build with: use a label like "Auto-Build version 34 attempt January 6, 2003".  Then perform a "Get by label" from source control.  Other engineers can stick more into source control without us worrying.&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;Ensure Validity&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;Of course, we still have to build the system.  A failed build tells us the system is not valid.  Hopefully this doesn't happen very often.  But here, also, is where we run our nice set of automated tests.  The more complete the test set is, the more confidence we have that the system we build is good.  Here's an important step, though: if even one test fails, we need to treat it as if the build failed in the first place.  The system is not valid.  This may seem extreme at first; we can worry about the 20% of the time when a fail doesn't matter once we're catching the 80% of the time when it does.  At that point, our tests should be catching these boundary cases for us, and we can still expect 100% of tests passing.  We want our code to be Ivy League material, after all.&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;Be Ready to Go&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;We want our build process to be as complete as possible - best case is that the build not only turns the source into a runable system, not only tests that runable system, but finally packages the system into the distribution form.  Java systems can get packaged into jars and even wrapped into the installation programs.  Native code can be built into the executable for and zipped up with the necessary README file.  We want to be able to grab a build from yesterday, or three weeks ago, and run it just as if it were the final release.  Because it might be.&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;Store Result&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;Now that our build is done, we need to keep everything in a place we can find it again.  Consider your source control for this; if we're Ready to Go with our installation files, we can check them in and let source control maintain the history.  Be sure to use labels with this to avoid configuration issues.  At the very least, we should keep a list of our builds available and named by date and build number.  With the price of storage today, redundancy is more than worth the cost tradeoff.&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;Minimal Cost Builds&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;Ultimately, we want our builds to cost very little in terms of time and space.  If two builds occur before source changes, we want to store only one result.  When a build is complete, we want to clean up our unneeded build materials and the source.  Why did we clean up first thing, then, if we're cleaning up &lt;span style="font-style: italic;"&gt;last&lt;/span&gt; thing, too?  In case something went wrong and we never got to the clean up step.  If we're going to clean up first then, why bother to clean up at the end?  Ideally we want a pristine system before and after the build; we really want our build to just get going, rather than taking the time to clean up after an old build.  Hopefully everyone will clean up after himself.&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;The Process&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;So, what then is the ideal build process?&lt;br /&gt;&lt;br /&gt;Step 1)    Clean up the build space (Start Fresh)&lt;br /&gt;&lt;br /&gt;Step 2)    Update the version number (Avoid Conflicts)&lt;br /&gt;&lt;br /&gt;Step 3)    Label the build components (Avoid Conflicts)&lt;br /&gt;&lt;br /&gt;Step 4)    Do a fresh full "Get" from source control (Start Fresh, Trust and Accountability)&lt;br /&gt;&lt;br /&gt;Step 5)    Build (Ensure Validity)&lt;br /&gt;&lt;br /&gt;Step 6)    Test (Ensure Validity)&lt;br /&gt;&lt;br /&gt;Step 7)    Package (Be Ready to Go, Store Results)&lt;br /&gt;&lt;br /&gt;Step 8)    Clean up the build space (Minimal Cost Builds)&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/31707900-115998365829292050?l=software-process.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://software-process.blogspot.com/feeds/115998365829292050/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=31707900&amp;postID=115998365829292050&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/31707900/posts/default/115998365829292050'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/31707900/posts/default/115998365829292050'/><link rel='alternate' type='text/html' href='http://software-process.blogspot.com/2006/10/building-ideals.html' title='Building Ideals'/><author><name>Carl Cox</name><uri>http://www.blogger.com/profile/11479857805045070539</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-31707900.post-115834229740110167</id><published>2006-09-15T12:39:00.000-05:00</published><updated>2006-12-16T19:53:42.787-05:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Software Development Process'/><category scheme='http://www.blogger.com/atom/ns#' term='Software Process Improvement'/><category scheme='http://www.blogger.com/atom/ns#' term='Software Process'/><category scheme='http://www.blogger.com/atom/ns#' term='Agile'/><category scheme='http://www.blogger.com/atom/ns#' term='Software Process Tracking'/><title type='text'>What is a Software Process?</title><content type='html'>&lt;span style="font-weight: bold;"&gt;Definition&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;In the beginning, there was nothing.  When the nothing was filled with problems, someone thought of how software could help.  This is where Software Process begins.  Software Process is the process of taking problems and solving them with software.  Problems come in, software comes out.  Typically, when people talk about Software Process, they mean a something like:&lt;br /&gt;&lt;br /&gt;Software Process: A series of steps which produce software.&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;But&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;In The Literature, in business, and in practice, we who talk about Software Process mean more.  We don't want "a series of steps"; such vague wording makes the lawyer and accountant in us shudder.  We want very specific results from a process, things like repeatability, predictability and improvement.  We want to know when our software will be done; we want to know that the software will be awesome, and we want next time to be done faster with yet more awesome software.  Of course, there are many Software Processes, but despite claims, they're not all trying to deliver these same goals.&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;Bytes&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;Even so, it's no wonder that elements from any one process look similar to elements in another.  Most of the time, processes cover specific tasks, like requirements gathering, software design, testing procedure, user feedback, and so on.  Some processes try to hide certain steps or role them together, but when it comes down to it, the old fashion "Waterfall" process had these steps down pretty well: Discover Requirements, Design , Code and Test.  Any software process is going to have to deal with these steps somehow; otherwise we're not really developing software.  Let's call this stuff Software Development Process.&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;Beyond Bytes&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;Software Process includes more than that, though.  Notice, our typical steps did not do anything for our extended goals.  Where do we get them, then?  In many ways, that depends on the process.  The Personal Software Process deals with these directly.  More time and attention is given to recording process step results than to defining the process steps themselves.  In this process, we record everything we can: how long we take to perform every step, how many defects we found in every step, how we fixed those defects and how long that took, and how long we spent distracted by the guy who wanted to gab about TV.  All this data gets recorded, compiled into a large and growing data set, and consulted whenever new work begins.  Sounds menacing to me, but it buys us predictability and reliability: we can say with increasing confidence how long it will take us to complete work and how many mistakes that work will have.  Some other processes try to do similar types of analysis but eliminate some of the paperwork overhead, but when it comes down to it, what PSP advocates is probably the best way to get good, hard, reliable numbers.  All this has to do with measuring our performance: let's call it Software Process Tracking.&lt;br /&gt;&lt;br /&gt;And yet, there's more!  Tracking progress is never an end in itself; writing a number down always leads to a question, "How do I improve this number?"  Whether we're dealing explicitly with these numbers, or implicitly within our process, improvement is a goal.  We always want to deliver better software faster; the only way to do that is to improve.  Usually, improvement mechanisms are codified in "Best Practices" or coping mechanisms.  When processes explicitly track things, we can confirm improvement equally explicitly.  Either way, let's call this Software Process Improvement.&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;Definition Redux&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;Software Process: Includes Software Development Process and may include Software Process Tracking and/or Software Process Improvement&lt;br /&gt;&lt;br /&gt;Software Development Process: A series of steps which produce software&lt;br /&gt;&lt;br /&gt;Software Process Tracking: A series of steps to record and analyze a Software Process which produces estimates of time, reliability, and other performance measures.&lt;br /&gt;&lt;br /&gt;Software Process Improvement: Tasks and practices that aim to improve individual and team performance in a Software Process.&lt;br /&gt;&lt;br /&gt;There's a lot to software processes, and not just whether they're Agile or not.  In fact, none of what we've talked about deals with Agile-ness of processes; that comes later.  But if we're going to develop software, and so use a Software Process, it's good to know what we're talking about and what we can get out of it.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/31707900-115834229740110167?l=software-process.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://software-process.blogspot.com/feeds/115834229740110167/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=31707900&amp;postID=115834229740110167&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/31707900/posts/default/115834229740110167'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/31707900/posts/default/115834229740110167'/><link rel='alternate' type='text/html' href='http://software-process.blogspot.com/2006/09/what-is-software-process.html' title='What is a Software Process?'/><author><name>Carl Cox</name><uri>http://www.blogger.com/profile/11479857805045070539</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-31707900.post-115566689995482546</id><published>2006-08-15T13:29:00.000-05:00</published><updated>2006-12-16T19:54:28.989-05:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Code Working'/><category scheme='http://www.blogger.com/atom/ns#' term='Software Process'/><title type='text'>Unpacking Packages</title><content type='html'>Many programming languages define ways of organizing code components into larger structures.  In Java, these are packages.  In C#, they are namespaces.  If our application is large enough to need multiple packages, how we define those packages needs serious consideration.  What are the goals of multiple packages in an application setting?  What should we look for?&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;Goal: Conceptual Integrity&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;First and foremost, we want our packages to mean something, to make a Statement.  The Statement should be simple and bold, and everything within the package should be geared toward that goal.  Statements like "THIS is how the user interface works!" or "Interact with networks here!" are good.  Statements like "talk to Databases and interact with users" are probably too complex, but we might be able to rephrase with "Let users manage databases" and be okay.  Conceptual Integrity allows people looking for solutions to know if this package is right for them, and it allows everyone working on our application to know if they're developing for this package.  It allows us to partition requirements into logical pieces, such that one requirement change will impact the smallest number of packages, and thus hopefully the smallest amount of code.  It's probably the single most important reason to have multiple packages.&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;Goal: Reuse&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;Just like we want methods reused and classes reused, we want our packages to be reused when appropriate.  We want to take that package we wrote for feature 1 and use it for feature 2. Probably this means some refactoring – the first pass may have been pretty feature specific.  It's worth the effort, though:&lt;br /&gt;&lt;br /&gt;   &lt;li style="margin-left: 40px;"&gt; Debugging one shared package will be much more fruitful than debugging two.&lt;br /&gt;   &lt;/li&gt;&lt;li style="margin-left: 40px;"&gt; Experience and statistics tell us that repeated code will result in repeated bugs.&lt;br /&gt;&lt;/li&gt;    &lt;li style="margin-left: 40px;"&gt; Testing one package is faster than testing two.&lt;br /&gt;   &lt;/li&gt;&lt;li style="margin-left: 40px;"&gt; Removing a defect in one package removes it from all components that use that package.&lt;br /&gt;&lt;/li&gt;&lt;br /&gt;We would love for that package to be useful in a completely different application.  If we can get someone else using it, any defect they find is one we don't have to look for.  Fix it, and make the package better for everyone.  Don't waste time trying to write the ultimate reusable package, though.  We're supposed to be writing an application, not a library.&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;Good Practice: Cautious Outer-App Package Dependencies&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;Maintenance is not just about requirements: we also have to worry about packages we depend on.  Every time a package dependency changes, we need to at least run through an entire testing suite.  At worst, we need to do a very big rewrite.  This means we want to rely on packages that aren't going to change much.  Note this doesn't necessarily apply to packages within our developing application; this means all those 3rd party packages we're trying to exploit.  Make sure they're solid.&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;Good Practice: Avoid Dependency Cycles&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;Dependency cycle: package A depends on package B which depends on package C, which depends on package A.   Avoid them.  For one thing, as my college Brian points out, if we have dependency cycles, we're probably violating conceptual integrity in some of those packages, and so we're losing the biggest use for our packages.&lt;br /&gt;&lt;br /&gt;Another reason cycles are bad: possible infinite testing.  If we have control over all the packages involved, we can cheat here.  Sadly, we don't always have that luxury.  Here's the problem:   Package A is updated, and package C needs to change in response. Now package B has to be checked and also gets updated.  Suddenly we're back to package A – dependency cycle. Without exclusive control over everything involved, this could go on ad nauseum.  The whole set, packages A, B, and C, might as well be collapsed into one big package while such a lock exists, and that huge package will not have a simple Statement.  We've just broken Conceptual Integrity.  Cry.&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;Good Practice: Package Ownership&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;For each package, define one person to be the "Owner".  The primary responsibility is to ensure the package maintains its conceptual integrity: that it remains true to its cause.  This person waves the red flag if something goes wrong with the package; this person watches for dependency cycles; this person probably writes lots of tests for the package.  This person is the package's mother.&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;Question: Where's the glue?&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;"Reuse is great and all, but we can't take Bob's Database Package and use it out of the box – we have to write special code to make it do what we want to do."  It's this glue code that makes an application something useful to Housewife Sally, who doesn't know or care about code.&lt;br /&gt;&lt;br /&gt;Whoa, slow down big fella.  Our packages ARE the glue code.  We're not writing libraries, remember?  We're writing an app.  It's okay to have a package where various pieces come together; somewhere in all this, after all, we need to RUN the program.  That can be a package Statement: "This package makes the program go."&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;Question: Dependency paths and fixing bugs&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;So, we've got this great package, but we found a bug.  And we fix the bug.  Good for us!  We're even pretty sure we fixed the bug without any repercussions; our whole super testing suite is solid and passes everything just fine.  This all means that packages that depend on us don't have to worry about anything, right?&lt;br /&gt;&lt;br /&gt;Wrong.  For one thing, we changed code.  "That means we may have injected a defect", says someone with super clean hands.  Small chance, maybe, but dependant packages can't take the risk – they're at least going to run through their test suite.&lt;br /&gt;&lt;br /&gt;For another thing, we may have changed something circumstantial that outside packages depend on.  Maybe we used to return a list sorted by last name, and now we return it sorted by first.  Doesn't matter to us, all we promised was a list, but somewhere someone realized they were all sorted one way, and used that fact.  Now that assumption (bad on their part) is broken, and they have to deal with it.  Not our fault, per se, something they have to take into account.&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;Summary&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;Developing to packages within our application is harder than developing just to our application.  Packages are intended to be reusable, which means more flexible.  More flexibility means more paths of use, and in turn means more possibility of defects.  This means more initial design, more development, and more testing.  Why program to packages, then?  All the standard, good reasons:  Abstraction, Encapsulation, Information hiding, Maintainability, Understanding.  Working hard to ensure we have a well architected system will save us down the road.  But we need keep a good head on our shoulders - it's easy to try to make things too flexible, too general when our app doesn't need it.  And the app is the reason we're here at all.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/31707900-115566689995482546?l=software-process.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://software-process.blogspot.com/feeds/115566689995482546/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=31707900&amp;postID=115566689995482546&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/31707900/posts/default/115566689995482546'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/31707900/posts/default/115566689995482546'/><link rel='alternate' type='text/html' href='http://software-process.blogspot.com/2006/08/unpacking-packages.html' title='Unpacking Packages'/><author><name>Carl Cox</name><uri>http://www.blogger.com/profile/11479857805045070539</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-31707900.post-115446289507281655</id><published>2006-08-01T14:13:00.000-05:00</published><updated>2006-12-16T19:54:46.580-05:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Algorithms'/><title type='text'>Password Protected</title><content type='html'>Today, passwords are like wild flowers.  Take your pick, you can have as many as you want.  Solely for work, I have four passwords - email, timesheet, and 2 different project repositories.   Wait, make that five, access to internal machines.  Purists will tell me that's ridiculous; all those (at least the first four) should be the same account, and so the same password.  Perhaps, but my IT staff aren't purists; politics (ie real life) gets in the way.  Besides, I don't want to complain about such things, I just want to know what my password is.&lt;br /&gt;&lt;br /&gt;When I get home, I another four or five passwords I use regularly: (personal) email, bank accounts, the all important nethack, Ebay, B&amp;N, ...  You get the idea.  I have so many passwords, I forget my last name.  Add on these important Good Password Tips:&lt;br /&gt;&lt;ul&gt;&lt;li&gt;No two passwords should be the same&lt;br /&gt;&lt;/li&gt;&lt;li&gt;No password should be written down&lt;/li&gt;&lt;li&gt;Should not contain any word in the dictionary&lt;br /&gt;&lt;/li&gt;&lt;li&gt;Passwords should be impossible to remember&lt;br /&gt;&lt;/li&gt;&lt;/ul&gt;Now add some of my favorite rules REQUIRED by some systems:&lt;br /&gt;&lt;ul&gt;&lt;li&gt;System A:&lt;br /&gt;&lt;/li&gt;&lt;ul&gt;&lt;li&gt;Total length must be at least 6 characters&lt;/li&gt;&lt;/ul&gt;&lt;ul&gt;&lt;li&gt;Case sensitive&lt;br /&gt;&lt;/li&gt;&lt;/ul&gt;&lt;ul&gt;&lt;li&gt;Must contain a number&lt;/li&gt;&lt;li&gt;Password must change every 90 days&lt;/li&gt;&lt;/ul&gt;&lt;li&gt;System B:&lt;/li&gt;&lt;ul&gt;&lt;li&gt;Must use three or more character classes (upper case, lower case, symbol, number)&lt;/li&gt;&lt;li&gt; Total length must be between 7 and 23 characters&lt;br /&gt;&lt;/li&gt;&lt;li&gt; Cannot be any of the most recent 3 passwords&lt;/li&gt;&lt;/ul&gt;&lt;/ul&gt;If you're like me, the set of rules is completely unrealistic.  I have to have 10-20 passwords that are not written down, impossible to memorize, longer than 6 characters, and tied to a particular account. &lt;br /&gt;&lt;br /&gt;Online tools that create pseudo random passphrases are okay, but every 90 days I have to remember another arbitrary string.  That's painful.  Here's the system I use to deal with all this.&lt;br /&gt;&lt;br /&gt;Pick a song, poem, speech, or passage to memorize.  It should be relatively arbitrary, but relevant to you.  In other words, it should be something you &lt;span style="font-style: italic;"&gt;want&lt;/span&gt; to memorize.  The Gettysburg Address, a Psalm, a Shakespeare sonnet, &lt;span style="font-style: italic;"&gt;Jabberwalky&lt;/span&gt;, anything works as long as it has multiple sentences and is at least a good paragraph length, say 50 words.  We'll use the following example:&lt;br /&gt;&lt;br /&gt;&lt;span style="font-style: italic;font-family:arial;" &gt;Once upon a midnight dreary, while I pondered, weak and weary,&lt;/span&gt; &lt;span style="font-style: italic;font-family:arial;" &gt; Over many a quaint and curious volume of forgotten lore,&lt;/span&gt; &lt;span style="font-style: italic;font-family:arial;" &gt; While I nodded, nearly napping, suddenly there came a tapping,&lt;/span&gt; &lt;span style="font-style: italic;font-family:arial;" &gt; As of someone gently rapping, rapping at my chamber door.&lt;/span&gt; &lt;span style="font-style: italic;font-family:arial;" &gt; " 'Tis some visitor," I muttered, "tapping at my chamber door;&lt;/span&gt; &lt;span style="font-family:arial;"&gt;&lt;span style="font-style: italic;"&gt; Only this, and nothing more."&lt;/span&gt; &lt;br /&gt;Now, whenever you need a password, pick a number.  &lt;/span&gt;&lt;span style="font-family:arial;"&gt;If today is the eighth, choose 8.  &lt;/span&gt;&lt;span style="font-family:arial;"&gt;Then we'll start with the eighth word: &lt;span style="font-style: italic;"&gt;pondered&lt;/span&gt;.  Now how many letters need to be in the password?  Say 10.  Then we look at the phrase starting at &lt;span style="font-style: italic;"&gt;pondered&lt;/span&gt; and counting for 10 words (treat punctuation like words):&lt;br /&gt;&lt;br /&gt;&lt;span style="font-style: italic;"&gt;I pondered, weak and weary, Over many a&lt;br /&gt;&lt;br /&gt;&lt;/span&gt;Take the first letter of each word, including punctuation again:&lt;br /&gt;&lt;br /&gt;&lt;span style="font-style: italic;"&gt;Ip,waw,Oma&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;Hmm.  That looks like a pretty good password.  Three character classes, fairly random.  Also, it's easy to memorize the pass-phrase: you already know it.  Here's another key: as long as no one knows your pass-poem (Poe's &lt;span style="font-style: italic;"&gt;The Raven&lt;/span&gt; in this case), you can write down key information.  Here, we start at the eighth word and use ten words.  Write down 8,10.  I usually write down lots more, because there's lots you have to remember if you don't use the password often:&lt;br /&gt;&lt;br /&gt;ebay, icarus, 8, 10&lt;br /&gt;&lt;br /&gt;The advantage of this system is that lots is kept in your head, but the tricky stuff is written down.  You memorize one poem and write down keys into that poem.  And, unless you're like me and tell everyone your system, people don't know what 8,10 means at all.  The pass-phrase is cryptic and the algorithm is cryptic.  It's not fool proof, but it's a lot easier than other methods I've tried for the long term.  (Don't write down your key next to your pass-poem!)&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight: bold;"&gt;Special cases: No Punctuation&lt;/span&gt;&lt;br /&gt;Some systems don't allow punctuation: then when counting for the phrase, skip punctuation.  Write down a minus to indicate you didn't use punctuation.  From before, using 8 and 10 again, we get&lt;br /&gt;&lt;br /&gt;&lt;/span&gt;&lt;span style="font-style: italic;font-family:arial;" &gt;pondered weak and weary&lt;/span&gt;&lt;span style="font-style: italic;font-family:arial;" &gt; Over many a quaint and curious&lt;span style="font-style: italic;"&gt;&lt;br /&gt;&lt;br /&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style="font-family:arial;"&gt;which becomes:&lt;br /&gt;&lt;/span&gt;&lt;span style="font-style: italic;font-family:arial;" &gt;&lt;span style="font-style: italic;"&gt;&lt;br /&gt;pwawOmaqac&lt;br /&gt;&lt;br /&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style="font-family:arial;"&gt;and you write down:&lt;/span&gt;&lt;span style="font-style: italic;font-family:arial;" &gt;&lt;span style="font-style: italic;"&gt;&lt;br /&gt;&lt;br /&gt;ebay, icarus, 8,10-&lt;br /&gt;&lt;br /&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style="font-family:arial;"&gt;Note the minus at the end indicates you ignored punctuation.&lt;/span&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/31707900-115446289507281655?l=software-process.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://software-process.blogspot.com/feeds/115446289507281655/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=31707900&amp;postID=115446289507281655&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/31707900/posts/default/115446289507281655'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/31707900/posts/default/115446289507281655'/><link rel='alternate' type='text/html' href='http://software-process.blogspot.com/2006/08/password-protected.html' title='Password Protected'/><author><name>Carl Cox</name><uri>http://www.blogger.com/profile/11479857805045070539</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-31707900.post-115437316588282662</id><published>2006-07-31T13:48:00.000-05:00</published><updated>2006-12-16T19:54:59.806-05:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='Code Working'/><title type='text'>C# Properties</title><content type='html'>The first time someone waved c# properties in my face, I smelled trouble.  It reminded me of other silver bullets I've watched fly my direction, and I wondered what low-grade thought process crafted those gleaming orbs from marketing hype.&lt;br /&gt;&lt;br /&gt;First, rough background.  In java, you write:&lt;br /&gt;&lt;pre&gt;public MyClass{&lt;br /&gt;private int myValue;&lt;br /&gt;public int getValue(){return myValue;}&lt;br /&gt;public void setValue(int value){ myValue= value;}&lt;br /&gt;}&lt;br /&gt;&lt;/pre&gt;In C#, with Properties, you write:&lt;br /&gt;&lt;pre&gt;public MyClass{&lt;br /&gt;private int myValue;&lt;br /&gt;public int Value{&lt;br /&gt;  get{return myValue;}&lt;br /&gt;  set{myValue=value;}&lt;br /&gt;}&lt;br /&gt;}&lt;br /&gt;&lt;/pre&gt;One of the "big benefits" of Properties is that you can treat them like fields:&lt;pre&gt;MyClass.Value = x;&lt;/pre&gt;But, when compiled, the properties get replaced with get_ and set_ methods.  This is a Big Deal (tm) to me; it means Properties are lying.  They're lying because you're calling a method, but you think you're calling a field.  The overhead possibilities are terrible.  You said &lt;pre&gt;MyClass.Value;&lt;/pre&gt; thinking you're getting a fast value back, but that call could be running off to a database, worse, on another machine.  You said &lt;pre&gt;MyClass.Value+=x;&lt;/pre&gt; and you just hit that database twice.   Convention says they shouldn't do that, but convention also says people shouldn't fly planes into buildings.  Who are you going to trust?&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;This doesn't bother me nearly so much: &lt;pre&gt;MyClass.getValue();&lt;/pre&gt; is telling me there may be some work involved.  I'm more okay with it running to a database and coming back.  I'm absolutely fine with it just returning a value.  My &lt;span style="font-style: italic;"&gt;expectation&lt;/span&gt; of a longish call was bettered by immediate response.  It's like getting a Wendys Value Meal, and they give you a free ice cream.  It makes you happy.&lt;br /&gt;&lt;br /&gt;Properties do the opposite.  I &lt;span style="font-style: italic;"&gt;expect&lt;/span&gt; them to come back immediately; when they hit a database, it's like getting that Value Meal and having no bread on the sandwich.  I'm kinda ticked, and I'm not going to go to that Wendys again.&lt;br /&gt;&lt;br /&gt;So keep your Properties to yourself.  I'm a happy man with my accessors and excessive parentheses and ice cream.  Take your silver bullet and get the jerk who stole your bread.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/31707900-115437316588282662?l=software-process.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://software-process.blogspot.com/feeds/115437316588282662/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=31707900&amp;postID=115437316588282662&amp;isPopup=true' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/31707900/posts/default/115437316588282662'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/31707900/posts/default/115437316588282662'/><link rel='alternate' type='text/html' href='http://software-process.blogspot.com/2006/07/c-properties.html' title='C# Properties'/><author><name>Carl Cox</name><uri>http://www.blogger.com/profile/11479857805045070539</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>0</thr:total></entry></feed>
