Best practices on separating debug/developing code java/javafx - java

I am working on a game in JavaFX and I'm sending people the compiled game once in a while for them to try out. As I'm still in the middle of developing it, I have several pieces of code intended solely for developing/debugging.
One example is a gamespeed slider that is of great use for me while testing, but it is VERY buggy and can only be used in a specific manner - in other ways, I don't want code like that in the test releases.
What is the best ways of removing such code?
Surrounding the code with if(Config.DEBUG) (setting a parameter in code) ?
Using if() but setting parameter in different build configurations?
Can SVN branches keep sort of code like this? Or should I change to Git?
Is there any way to use annotations for this?

SVN branches can be used for this, but you keep ending up with the effort of having to merge your branches every so often. I wouldn't do this.
Though perhaps not wildly elegant, I'd go for your first suggestion: Put a configuration parameter somewhere that your build process can change it for you automatically, and if()s around the affected code.
Change your build process so it will create player jars and testing jars at the same time.

Just use pure if statements, and check if some environment variable or VM option is set, in which case execute your debug code (or test release code, depending on your needs). There should be no performance issues, and the HotSpot JIT might even eliminate these parts.
Sure, it feels somewhat quick-and-dirty to me, but it's simple and it does exactly what you need.
Regarding your other suggestions, using a branch is not a good idea to do this. It's possible, but it will have an overhead you don't really like to deal with. Annotations might be able do the job, but this solution will be more complex than necessary.

Related

Is there a way to feed in different values from a table to Cucumber background? Make background dynamic?

I have a Feature file and the background step is pretty simple. However, the setup done in that step needs to be working with two different types of values and it is applicable to all the scenarios within that FF. Is there a way we can make this background dynamic?
Example: I want to do as below:
Background:
Given hospital configuration is done using '<some config>'
|some config|
| abc |
|xyz |
There are three ways I can think of to run a feature file twice, one with one configuration and the other with another configuration.
Duplicate the feature file and change the background so that it specifically loads the particular configuration.
Before dismissing this solution look at some of the positives.
its very simple
its easy to document (just put comments in the preamble about the duplication)
it supports customization specific to a particular profile.
The last point is worth expanding on. If the behavior is identical with each profile then what is the point of the profile. Basically you are saying it has no effect at all. If it has not effect at all then why are you testing it. If the behavior varies between profiles then you really want to explore and express those differences.
Run the feature twice by using an external setting.
This basically comes down to having Cucumber pull the setting from the environment and running cucumber twice, once for the first setting, and then again for the second setting.
So something like
SETTING=abc cucumber ...
SETTING=xyz cucumber ...
Use an around hook to run the internals of a scenario twice.
Here you are putting a tag on the feature and making a custom hook to run the scenarios twice. This is equivalent to the second solution but you are embedding the mechanism inside a single run of the features.
In ruby this would look something like
# run_twice_hook.rb
Around(#run_twice) do |scenario, block|
load_first_setting
block.call
load_second_setting
block.call
end
I think this solution comes closest to what the OP wants.
I also think this is the worst solution, because its technical, tricky, hidden and embedded inside the feature run. Its expensive to implement and expensive to maintain, and it probably hides an underlying business problem (mentioned in the first solution)
So please use this solution with a great deal of caution. In general with cuking simple is best, and a bit of repetition is preferable to technical complexity to avoid repetition.

Is it ok to have unused Components in project?

Generally unused/dead code is bad but I wonder what to do with unused components.
Imagine that I have application that sends notifications to users, it sends EmailNotification but after some time we switch to sending notifications with SMS. Instead of deleting EmailNotification class i create interface let's say Notification and I have such structure:
Notification
--SmsNotification
--EmailNotification
I don't want to remove EmailNotification, because after some time we can go back to EmailNotifications and this change will be as easy as mark EmailNotification class as #Primary.
In such case one of the implementations is always dead code and I wonder if it is ok or generally how to deal with that?
Actually this is not the best practice.
Instead of this practice, you can separate your code into two different modules, one per component. By this way you can utilize any of two modules depending on your needs through your build automation tool (maven or gradle for example). So the produced jars will contain no dead code.
I would agree that this is not dead code, just unused code. However the code in production should be as clean as possible and so if using version control such as git, I would remove the code as it will always be there in the history of the git repository. If you do not want to do this, then I would suggest a way of explaining why the code is there, some thing like a java doc or readme file.
There should not be any problem in keeping the old code, which might become reusable in future. As a matter of fact, the design itself should be so that it can accommodate changes in components without severe impacts.
But if there is an unreachable block of code, which certainly will not add any value to the product in present or future, it will be better removed, because it will unnecessarily increase the number of lines of code and will slow down the process of testing, ultimately impacting the delivery. Additionally, this unused code block will also appear in the final product (the JAR/WAR) unwantedly increasing its size.
In my case, I was using SonarQube for static code analysis and there were blocks of code, methods and sometimes files which will show up only at the time of testing. It was slowing down the process as well as taking otherwise unnecessary heap space. Getting rid of those blocks certainly helped us speed up the process.
One thing you should be aware of is that even unused components need to be maintained. Some examples that come to my mind:
If the Notification interface changes, EmailNotification has to be changed too
If you update dependencies used by multiple components, you by might need change EmailNotification too
If you change or introduce new quality measures (e.g. x% of code coverage, specific code styles, no warnings policy etc.), they also apply to unused components - which leads to additional work
The changes required to maintain unused components could be obvious (because it does not compile any more) or subtly (they still compile but since they are not used, no one notices that they fail at runtime). Even if compile errors get fixed, chances are that they are not getting tested properly.
So by keeping unused modules you might have to do more work than necessary for certain changes and you still run the risk of having a broken module that you can't just turn on when needed. It could easier to just retire the component and revive and update it when it is actually needed. You could wait with the retirement until there actually is a breaking change though. If you are lucky, no breaking change comes before the component is needed again.
If you are certain that you'll need the component again in near future, then keep it. But make sure to maintain it properly.

How to refactor procedural start-up code?

I have a class (Android Activity) which handles start-up of my application. The application has some pretty complex start-up rules. Right now it looks like a bunch of spaghetti and I'm looking for strategies for refactoring it.
It's honestly such a mess I'm having problems hacking it down to provides pseudo code. In general there are some rules for start-up that are basically codified in logic:
Steps:
Check for error on last exit and flush local cache if necessary
Download settings file
Parse settings and save settings to local native format
Using the values in settings, do a bunch of 'house keeping'
Using a value in settings, download core data component A
Parse component A and load up local cache
During this logic, its also updating the user interface. All of this is handled in a zig-zagging, single monolithic class. Its very long, its got a bunch of dependencies, the logic is very hard to follow and it seems to touch way too many parts of the application.
Is there a strategy or framework that can be used to break up procedural start-up code?
Hmmm. Based on your steps, I see various different "concerns":
Reading and saving settings.
Downloading settings and components (not sure what a "component" is here) from the server.
Reading and instantiating components.
Flush and read cache.
Housekeeping (not really sure what this all entails).
UI updates (not really sure what this requires either).
You might try splitting up the code into various objects along the lines of the above, for example:
SettingsReader
ServerCommunicationManager (?)
ComponentReader
Cache
Not sure about 5 and 6, since I don't have much to go on there.
Regarding frameworks, well, there are various ones such as the previously mentioned Roboguice, that can help with dependency injection. Those may come in handy, or it may be easier just to do this by hand. I think that before you consider dependency injection, though, you need to untangle the code. All that dependency injection frameworks do is to initialize your objects for you -- you have to make sure that the objects make sense first.
Without any more details, the only suggestion that I can think of is to group the various steps behind well structured functions which do one thing and one thing only.
Your 6 steps look to be a good start for the 6 functions your init function should have. If #2 was synchronous (I doubt it), I would merge #2, #3 into a getSettings function.

Understanding a large Java program

I am working on a java project and I have to extend (add more functionality) it. But I don't know how should I learn the existing one before incorporating them.
Is there any specific path I should follow?
Can I run it in a way so that I can see, statement by statement, the execution of the program?
I am a kind of stuck in understanding it, thanks.
Here is another approach that is hacky, but I've found useful in the past when unable to attach a debugger. If there is a piece of code that you are looking at, but are having a hard time figuring out who is calling it you can throw a new runtime exception, catch it and print the stack trace.
try {
throw new RuntimeException("who is calling me");
} catch (RuntimeException e) {
e.printStackTrace();
}
You can always fire it up in a debugger/your IDE of choice and step through it all you want, though it's probably best to find someone who is more familiar with the source to provide you an overview, or to look for documentation on where to start.
Pick one piece of functionality for which you understand the requirements. Find the entry point for that feature and follow the code for that one feature. It should give you a good understanding of how the architecture works.
Integrating with code that is already written can be very difficult. In my experience, some of the best clues I've gotten about already-written code come from the method signatures (the mapping of the function's input to its output). The method's signature can give you a lot of hints about a program, namely where and especially how that particular method fits in the context of the larger program. Usually, a method signature coupled with a descriptive method name can give you enough information to be dangerous, especially in a typed language like Java.
Although I wouldn't suggest running the code line by line and looking at changes (because this usually amounts to tons of work) but for really ugly but important code sometimes it is necessary (I've definitley done it before using DDD for C programs). In this case, a quick google search reveals http://www.debugtools.com/ , a graphical java debugger, which may do the trick; there also seems to be version of DDD that works with Java.
This is a recurrent question on Stack Overflow. There is already very good answers all around:
https://stackoverflow.com/questions/3147059/taking-over-a-project
Cleaning up a large, legacy Java project
https://stackoverflow.com/questions/690158/how-do-you-learn-other-peoples-code
Also, this book might help: Working Effectively with Legacy Code
"Patience and fortitude conquer all things." - Ralph Waldo Emerson
I would recommend you to start with the debug as well so you can go through the program step by step.
Documentation:
If you have documentation, it’ll be helpful. But it can be a pitfall, as much documentation is out date, they can be misleading you.
Bugfix:
You could start with bugfix or new feature implantation. Start work with small scope, it’ll be easy work. During the bugfix, you could understand the code more and more.
Baseline the code, I generally would use git
Do a build of the application
Run it.
If baseline fails build or process is too complicated, create a branch and fix it
Create a branch and modify a string or something that would show some visible change if you modify the code.
If Javadocs are not created via ant or build files, create a new branch to do this.
If there is no JUnit test cases (or if there are but they don't work), create a branch and fix it.
Create a new branch to do the merge.
The following is if you're using Eclipse or similar product
If you're the only developer, create a new branch and set up project settings for code formatting and cleanup. Then execute the code formatting and cleanup. This would allow you to have a more stable baseline for future work. If not, try to coordinate with others.
Install FindBugs, Checkclipse, PMD to do some simple checks on the code base. Looking at WTFs sometimes will give you a better idea on how things are working (or not)
Install Eclemma and see how much of the code is actually tested.

When to use JAF activation

I wonder if I should use it, in this example. I'm reading files, and I need to store one parameter with that file.
According to this parameter I'm bundling files together and sending them over the wire.
I came accross jaf activation framework, and I'm not sure if it is appropriate to use it in such simple example.(store 'file' into DataHandler with this parameter or to make me simple holder). Of course I don't know if requirments can change in the future, and I will need more.
What do you think about it?
My impression is that it's too much, it's difficult to get proper sources. But on the other hand it has what I need.
The question could be more general as well, should I use framework which can do a lot more, if I need something really simple and I can code it quickly?
thanks in advance
To answer your more general question, I would most often make use of frameworks wherever possible.
It's always possible that you're going to want more functionality in that area. If you're using the framework then great. Otherwise you have to back out and rewrite. Or maintain two different implementations.
Frameworks have been debugged/tested etc. and will handle the edge cases. Often what you think of as being trivial ends up more complicated than you first thought.
Don't forget that due to how class loading works, the JVM will only load the classes you require. Consequently you're only affecting the size of deployment of your application, not the runtime size (by referencing a sizable jar)

Categories

Resources