Scripting on Windows
There’s this flame war between Linux and Windows. Like Linux is user-friendly, it’s just more selective with its friends. Another one is, that it’s easy if you don’t mind clicking. Windows 10 contains a bash shell, still, this won’t end just now.
Obviously, I install them because we’re not using Windows 10 yet. Also, I’m installing mingw because git-bash is based on that. Still, this isn’t the real reason.
Why is it useful?
The real reason is that I can solve complex problems quickly. Say for instance, the jd-gui had some problems. It couldn’t decompile some classes and it wouldn’t save all the decompiled sources either. I could’ve downloaded some other versions and played with them. However, I already had mingw and procyon on my machine so I started to write a for loop. In a couple of minutes I had this:
cp -r classes sources # this creates a paralel directory structure find sources -name '*.class' | xargs rm # this removes the class files # a for loop through the classes. I could've excluded the inner classes too.. for f in `find classes -name '*.class'`; do # creating the name of the destination java file j=`echo $f | sed -e 's/^classes/sources/g' -e 's/.class$/.java/g'`; # invoking the decompiler java -jar /f/Programs/decompilers/procyon-decompiler-0.5.30.jar $f > $j; done
The point here isn’t the code. Bash can do loops, branches, and other stuff in a weird way. The point is that I could substitute some gui functionality with some code in a couple of minutes. It took as much as starting up eclipse and creating a new project.
So, I wrote this one-time script. There are a few enhancements I could’ve made.
I.e. this is how you can filter out the inner classes from the decompiler loop:
for f in `find classes -name '*.class' | grep -v '\$'`; do #... done
But deleting them isn’t much harder either:
find . -name '*.java' | grep '\$' | xargs rm
I can also mass-edit the decompiled classes:
# a loop for the java sources for j in `find src/ -name '*.java'`; do # retrieving the java class name from the path f=`echo $j | sed -e 's/^.*\///g' -e 's/.java$//g'`; # creating the command - it will be useful for debugging cmd=`echo "sed -i 's/\b$f\.//g' $j"`; echo $cmd; # some feedback during the script run eval $cmd; # invoking the actual command done
As you can see, I’m using sed and command substitution extensively. There might be other approaches that I’m unfamiliar with. Still, these tools help me a lot to solve complex problems quickly.
What are your favorite command-line tools? How could you improve these scripts?