I think writing code is an "art", it has to be intuitive, free-flowing, easy to understand and maintain. It is easier said than done. Hence, some guidelines should be followed.
The following are guidelines that help achieve this. These are gained (some learnt and discovered) over my last 11+ years of software development experience. Primarily they are java centric but (in most cases) apply to other programming languages as well.
Naming Conventions:
1. variable naming - a variable name should be descriptive and in camel case. It is a noun. Best is camel case e.g. secondsPerMinute. If a variable name is used multiple times in the code, better to shorten it and put a comment. e.g. fooCount can be fooCnt with a nice comment that it stores the number of foo in the system. adding context to the name helps understand the code better. Avoid a, b, j as names, use "counter, index" instead for simple counter variables in loops instead of j,k.
Sense tells me that there should be a limit to the length as well. Try to use sensible short forms for words if the full-form makes the length goes beyond 25 chars. e.g noOfEmployeesInAfghanistan can be emplInAF //not bad!
This applies to all types of variables - local, class-level, method parameters.
2. constants - general guideline is to use CAPITAL_CASE (or UPPER_CASE) with an underscore separating words.
3. function naming - should again be descriptive and in camel case. It is a verb. e.g. getDefectedCars(), calculateFoo() etc. Overloaded methods with same type and no. of arguments are better distinguished by including the differentiator in the method name. e.g.
5. Package names - they are flatcase with each word separated by . e.g. com.hgoyal.metrics.domain
Class Design
1. Should be catering to a single functionality or domain.
e.g. a separate class for reading data from the database, a different class for accessing cache, different for transformations.
2. Always extend an Interface or more appropriately first define an interface then a class implementing it.
3. Avoid very long classes - bigger means there is scope to split into multiple.
4. Carefully pay attention to declaring members as public, protected or private. Limit the visibility as much as possible.
5. Methods should be small in size, encapsulate logic in smaller methods.
6. use composition over inheritance.
7. use "design patterns" as much as possible with appropriate tweaking.
Organization
1. Organize classes into meaningful packages. again pay attention to growing package size.
The following are guidelines that help achieve this. These are gained (some learnt and discovered) over my last 11+ years of software development experience. Primarily they are java centric but (in most cases) apply to other programming languages as well.
Naming Conventions:
1. variable naming - a variable name should be descriptive and in camel case. It is a noun. Best is camel case e.g. secondsPerMinute. If a variable name is used multiple times in the code, better to shorten it and put a comment. e.g. fooCount can be fooCnt with a nice comment that it stores the number of foo in the system. adding context to the name helps understand the code better. Avoid a, b, j as names, use "counter, index" instead for simple counter variables in loops instead of j,k.
Sense tells me that there should be a limit to the length as well. Try to use sensible short forms for words if the full-form makes the length goes beyond 25 chars. e.g noOfEmployeesInAfghanistan can be emplInAF //not bad!
This applies to all types of variables - local, class-level, method parameters.
2. constants - general guideline is to use CAPITAL_CASE (or UPPER_CASE) with an underscore separating words.
3. function naming - should again be descriptive and in camel case. It is a verb. e.g. getDefectedCars(), calculateFoo() etc. Overloaded methods with same type and no. of arguments are better distinguished by including the differentiator in the method name. e.g.
- getEmployeeById(String employeeId),
- getEmployeeByName(String employeeName)
5. Package names - they are flatcase with each word separated by . e.g. com.hgoyal.metrics.domain
Class Design
1. Should be catering to a single functionality or domain.
e.g. a separate class for reading data from the database, a different class for accessing cache, different for transformations.
2. Always extend an Interface or more appropriately first define an interface then a class implementing it.
3. Avoid very long classes - bigger means there is scope to split into multiple.
4. Carefully pay attention to declaring members as public, protected or private. Limit the visibility as much as possible.
5. Methods should be small in size, encapsulate logic in smaller methods.
6. use composition over inheritance.
7. use "design patterns" as much as possible with appropriate tweaking.
Organization
1. Organize classes into meaningful packages. again pay attention to growing package size.
2. Choose different folders or source code, test cases, images, static content like html, jsps, javascripts.
src/main/java - for java source files
src/test/java - for corresponding test files - the package names for test classes is same as the package name for source classes. See below:
resources - for test case inputs, images.
WEB-INF/images/ - for images
WEB-INF/html/ - for html files
WEB-INF/js/ - for javascript files
3. a read-me.txt file at the root of the project containing a brief description about the project and its usage helps.
4. Always format the code to ensure consistency. Stick to a "brace" convention - e.g.
for ()
{
}
or
for () {
}
Needless to say that nicely formatted code is easier to read, debug, understand.
Documentation
1. This aspect is as important as rest of the above. Self documenting code should address 50% of the documentation concerns, but it is also essential to provide additional documentation for fairly involved logic snippets, methods, class usage, use case patterns, edge cases, possible exceptions and errors.
2. Do write class level, method level comments. use java-docs format for java.
3. package-info.java gets created by Eclipse IDE for writing a brief about the package. It gets used by the java docs.
4. Generate java docs and ask for review from the end users/incorporate feedback. add version, date, author info wherever necessary. refer to other classes/methods in the documentation wherever necessary.
Error Handling & Logging
1. Use logging as much as possible.
2. Choose log level carefully from - info, debug, warn, error, fatal.
3. Check to see if the logger implementation used is an asynchronous one. If not extensive logging can lead to a lot of IO, hence degraded performance.
4. Tune logging configuration appropriately. There are ways to turn off logging for a library at a package level or to choose the logging level at package level. Check for log file size, log rotation policy.
5. Log statements should be consistent as well. Use string formatters.
6. Consider confidential information is not logged e.g. passwords, information which is stored as encrypted.
7. Use error codes mapped to error messages. Consider externalizing this either in a database table or a config file. Consider for internalization use cases.
8. Basic information like sessionID, transactionID, threadID, userID should always be associated with the log statement. Very important.
9. Throw exceptions as and when necessary. Use exceptions that come with the JDK instead of inventing your own. e.g. IllegalArgumentException, FileNotFoundException etc.
Unit Testing / TDD
Always write a test case for the new functionality added. Ensure to cover all paths in the method by writing multiple tests. A coded test case helps in a long run when the method is tweaked after a long time and a quick way is needed to ensure it hasn't broken rest of the functionality. Well tested code with working tests should be only checked in to the repository.
No comments:
Post a Comment