We programmers are optimists. This manifests itself in the entire software development cycle from estimating deadlines to writing code and implementation. As my practice shows, in the development of software Murphy's laws work in 100% of cases. Despite this, I encounter “optimistic programmers” over and over again.
Top “optimistic” assumptions:
We can still release this week on Friday at 5:48 p.m., although there are errors in the code.No you can not. In addition to fixing errors, you need to:
- To control / pull this code (you do not conduct development in the branch from which you publish in production, right?)
- Publish code on a test bench and test, including regression
- Check configuration, database migration
- Save production
- Post Changes
- Test Production
- Roll back if something went wrong
Even if everything happens in automatic mode, you will hardly have enough 12 minutes before the end of the working day to finish. Usually such calculations are done in a hurry and end with silly mistakes on production, processing at night and / or on weekends, rollbacks to the previous release and transfer of the calculation, or a combination of these points.
The decision on release / release can be made only after the code is written and tested. Know exactly how long the calculation, backup and rollback to the previous version in the case of epic files take. Always lay the most pessimistic option: you will give your best and you, for one reason or another, will have to roll back. On the current project, we automated all the calculations and backups. It takes 10 minutes to calculate, restore from backup: 10 minutes, minimum smock testing: 2 hours. Means, for the calculation on production, I lay 3 hours of time.
It takes three days. Can you do it in a day? Well, maybe I canDo not follow up with managers. The manager, even with a technical background, does not know the whole story. What may seem like a simple and quick manager can actually take a lot more time. The manager always evaluates only the laboriousness of implementing a new feature. Your task is to insist that you need time for refactoring, testing, calculation. Following the lead of management, over and over again you will postpone technical debt until it accumulates so much that you will not know which side to approach to refactoring. The requirements are changing, no one can immediately write the perfect code, no more and no less than required. If you feel that crutches in this place come around for days and weeks in the future, it is better to spend the extra few hours now and pass the feature a little later. Explain this to the manager in his language: Now this refactoring will cost us at 8 o’clock. And if we insert crutches, then in a month our technical debt will cost 56 hours. Managers usually count well, and easily multiply the number of hours on your rate. Remember that no one except you knows the code better, so you better know how to do better on the technical side. You can read more about management pressure in the article “How are two weeks ?! ".
Oh, this is a very stupid bug, now I’ll fix it quickly and it will work. Test to write to nothingNo, a bug is an occasion to write a unit test. If it appeared, it means that you missed this behavior and you have a hole in the "code coverage". Found a bug? Add the unit test / integration test / test case to the test plan. This will eliminate the "boomerangs" - bugs that come back again and again.
This is a very simple feature, you can not even add it to the task tracker. I will do so, the requirements are clearNo, the requirements are probably more complicated than it seems at first glance. It is possible that new requirements will conflict with existing system behavior. If you do not add task to the tracker, then in any controversial situation you will be extreme. The worst option is an oral arrangement. People have a very short memory. All tasks should be set in writing only. I wrote in detail about requirements management in the article “ Specification By Example - BDD for Pragmatists ”.
You can not publish this change to the test stand, it works fine on my local machine. Running tests is also a waste of time, here everything is so simpleNo, always test, first of all, on the “target” environment / hardware. Any emulation is just a model. In real conditions, unforeseen circumstances may emerge: a different version of the OS, other rights, a different processor power, RAM, other open ports. Anything.
This check is useless. It would never occur to anyone to use the program in this way.Extra checks do not happen. Exactly for such cases, exceptions were invented. You do not support any behavior / scenario? Throw a NotSupportedException . Everything will be very clear. But worse than NullReferenceException, it's hard to imagine something. This does not provide any information to the person supporting your code. He does not have to rummage through the stack trace and look for low-level errors. Always handle low-level errors and use your understandable exceptions. In .NET, an exception has an InnerException property that helps keep information about a lower-level problem. Not bad about exception handling in .NET is written in the article “ Safe Work with Exceptions in C # ”.
You can handle this error and pretend that nothing happened.Empty try-catch blocks usually appear when reliability and fault tolerance appear in software requirements. This behavior is equivalent to trashing under the carpet so that no one sees. If you need fault tolerance, consider an emergency system restart. The first thing you should do is to log the exception and tell the developers. You can send letters to developers in case of errors, you can use instant messengers, there are a lot of options. The worst thing you can do is ignore the mistake, because you do not know what the consequences are. The word "exception" is not just chosen. This emphasizes that the behavior is not planned and not normal.
This is not a bug, this is a feature, on the test the database is empty, everything will be fine on productionNo and no again. If the data must be in the database, then include it in the calculation. Have you changed the configuration? Add a config transformation. If a case is not verified, in 9 out of 10 cases there will be an error in it. At such a stand it is impossible to hold a demonstration. “A mistake creeps out here, but it won’t be on the battlefield” - it sounds awful. If for some reason it is impossible to set up a test stand identical to production (financial transactions, paid accounts, security settings, etc.), use stubs, emulators and similar test accounts. Bring your test bench closer to production as much as possible.
I fixed / updated, it seems to workNo "like." If there was any kind of error on the stand, check that after your fix / update, nothing else broke. Get the minimum checklist of the application health check after the update, for example: log in, buy something, see a couple of pages. This will save testers and your fellow developers from repeated calls to you: “Look, the goods are reception, and the old error has disappeared in the news, but a new one has appeared.” Take this test for granted, as an element of personal hygiene. You don’t think about why brush your teeth and wash every day.
FIG knows what the problem was, I restarted, it workedNo "FIG knows. You must accurately understand and suppress any possibility of a program crash. If you solve the problem by restarting, you are not fighting the cause, but the effect. This problem is guaranteed to be repeated at the most inopportune moment. You will be awakened in the middle of the night so that you will restart the application once again because it has “fallen”. Always solve the problem completely. Does the app need regular reboot? Configure automatic restart, localize the problem, add task and fix it. Very well about the dangers of "hatred" is written in the article " What is bad about working for the result ."
The implementation of the above recommendations requires self-discipline. It’s hard to follow them, but Murphy’s laws never let me down. Every time I make an exception, something unexpected, extraordinary and unplanned happens. Every time I can’t get the job done on time and on time, I get upset, so I try to never back down from these rules. As a result, I am much more optimistic than before looking at software development in general. I know that there are no “too complicated” tasks. There are tasks that require a lot of time to implement. I hope that my checklist will be useful to other developers.