Wednesday, February 22, 2012

How to read a file in Xcode project

Recently I got stuck with an objective C problem, Given a text file in your Xcode project, how could I read this text file in my Xcode 4.2 project?
For example, you got a text file called test.txt, it has some contents. In your Xcode project, you need to read its file and print its content. It sounds easy at the beginning, but end up really tough, especially you are new with the latest version of Xcode.
The key problem is you need to make sure the file test.txt is put as the same folder as the build target file, which is the Products folder, otherwise you will always get the file not existed exception.

Through several times try out, finally I figure out how to do it.

1. Add your file into project
   Select File - Add File into xxx, chose the created file into project.
2. Add a "copy file" build phase
    View - Navigator - Show Project Navigator, chose Project, select targets, select Build phase,
    and click "Add Build Phase", add "Copy files";
    in the new Copy Files build phase, choose
      Destination - "Production Directory"
     and click "+" symbol, then choose the file test.txt in your project.

How to test if the file was added in the Product folder or not?
After press the "Run" button, you will see the executable target file under the "Product" folder of your Xcode project,select the target file, right click, select "Show in Finder", then the Product Folder will pop up in the Finder Application, then you should see the test.txt file in the same folder.

Monday, February 13, 2012

Jeremy Lin - an inspring story

Last week NBA belongs to Jeremy Lin!  he just exploded to a star from an unknown underdog, leaded his team 5 wins in a row in a week! What a amazing true cinderella story! I watched his game vs. Lakers last Friday. I was really enjoying the game: he demonstrated his basketball skills and talent: he is smart, he got a high IQ in the basketball. I like his personality: confident, calm and humble. I think these will attribute with his Christian religion, Harvard graduate background and his Chinese descendent. Jeremy's successful story made me realize that Basketball can be played like this: you don't need a very strong, very tall or very fast body, if you have a regular body but you are smart enough and hardworking, you can be a good player as well, like Jeremy Lin! The IQ and skills are more important than the body.

Now I becomes his fan, his story is really inspiring, I learned:
- Always have a big dream. Don't limit your self. You don't have to be genius, you need hard working.
- Craft your skills, practice hard. Jeremy's success is not by accident. I can feel behind scene he must be a hard worker. Since those skills can not be done in a short time.
- Be patient and prepared for the opportunity, you can only seize the chance when you are prepared.

I hope his lin-sanity keeps going!

PS:
 Jeremy Lin's blog
 His facebook page
 Youtube




Using Groovy to update/generate XML file


Recently when I refactored the Android framework in my work, I found I need to generate eclipse .classpath file based on the library file.
I found using Groovy XML library is a lot easier to do this job compare to Java.

1. Add a new library to the current .classpath file.
Problem:  You have a Eclipse .classpath file, which is XML, you need to add another jar file in the class path. for example, adding following into the .classpath:
Solution:
 If you want to write the output to file, use the following code snippet:

There is another method to print XML, using XmlNodePrinter, like:
But I found using XmlNodePrinter will not generate line break, and no xml header either.

2. Generate a new .classpath file
Problem:  iterate the libs folder, add all the jar file name into the .classpath file.
Solution:

Thursday, December 22, 2011

Why I decided to take Scrum training?

Yesterday I registered an Certified Scrum Master training.  I choose the seminar on Jan 12, 2012  from Berteig Consulting.  Actually I am not so interested in SCRUM, rather I am super fan of Lean/Kanban, XP and software craftsmanship.
I have a bias on SCRUM because I feel its process is oversimplified, and focus on manager side only, ignores developer side; and it lack the whole picture of Lean and flexibility of Kanban. Another reason is so far I did not find a good SCRUM example in my past experience, so I really doubt the its performance.
The third reason is recently I found many articles which pointed out the issues of SCRUM.

As a many years of working experience as a software developer, I really doubt a certificate is useful.  I don't think that you will become an SCRUM master just for 2 days training, which means master Agile philosophy is too easy.

But recently I changed my mind, and decided to get a SCRUM Master certificate. You may wonder why I changed my mind so quickly.

Why learn Scrum?
1. I realized that the current IT situation is that  Scrum is still the de-facto process, even though Lean/Kanban is really hot inside the Agile community, but outside of the community, Scrum is still the most popular one. I will say 90% of the IT managers does not know Kanban. They are  more familiar with SCRUM.  If you have a Scrum training or get a certificate, it will be helpful for your career path. My long term goal is Agile coach, so I hope I can use CSM as a business card to help me find better jobs.

2. I hope the CSM certificate can help me make changes in my company. 6 month earlier, I tried to suggest to my managers thinking of using Lean/Kanban, they are familiar with Scrum, but not Kanban. I found I get stuck, because I don't know how to persuade them, since neither I have Kanban experience, nor I have Scrum certificate. Now there are 3 Scrum Master in our company. I hope if I have a Scrum certificate, then I could use their familiar "Scrum" language to communicate, then it would be easier for me help the company to transform from Scrum to Lean/Kanban.

What do I want to know about Scrum?

  • Clear the misunderstandings about Scrum;
  • Focus on the principles and philosophy behind Scrum;
  • Figure out the fundamental assumption which support Scrum;
  • Find out the good and bad parts of Scrum;




Monday, December 12, 2011

Cynefin framework and software code

Recently I read some article about Cynefin framework, it is really inspiring. As the diagram shows, cynefin framework categorize the problems in to 4 domains:

  • simple
  • complicated
  • complex
  • chaotic
For different domain, the approach and strategy are quite different.
Today I would like to analyze the software code using cynefin framework.

Which domain does software belong to?
In General I will say software belongs to complex domain. One reason is software product environment changes so fast, the other reason is its entropy nature: always grow from simple to complex. Software product is so hard to predict and plan. That is the reason why we choose agile methodology: we follow TDD, keep refactoring, iterative developing and continuous integration. These methods are to deal with rapid the software's rapid changing context.
Let's compare the complex domain with agile practices:
complex, in which the relationship between cause and effect can only be perceived in retrospect, but not in advance, the approach is to Probe - Sense - Respond and we can sense emergent practice.
Here The probe - sense - Respond is same as TDD and iterative development, since we don't understand the domain, so we have to rely on immediate feedback.
And the emergent practice and retrospection, which is the same as refactoring, refactoring itself is emergent practice.

We can also conclude that the reason why waterfall does not working is because they assume the problem domain in software is always in simple domain.  

How about other domains?
If we don't care code base and let it grows, then code base will becomes more and more complex until it becomes chaotic. As a developer we all have the experience of working with messy legacy code base: the messy code is hared to understand, hard to maintain; you fix one issue, then will generate another issue unexpectedly; the software is unstable, a small change will cause a big issue; the issue is always unpredictable;nobody understand the system; we spent all the time putting fires. Which is totally unstable and uncontrollable. These symptoms fit nicely with the chaotic domain model.

But if we keep writing clean code, the code are easy to understand, easy to maintain, easy to change. In agile world writing clean code also means simple design. So this  will fit nicely in simple or complicated domain. Since they are both ordered. so they are manageable and controllable. That is software's ultimate goal -  flexibility, maintainability and reusability. So we will say clean code will help the software reduce the complexity.

Why clean code will help reduce the complexity?
The following tools and method help us writing clean code:
  • SOLID principles
  • high cohesion/loose couple
  • Design patterns
  • DRY principle
  • LoD principle
  • Refactoring
Lets' dig them deeper:
Break the unnecessary dependencies
   Uncle Bob once said writing software is all about dependency management. SOLID principle, high cohesion/loose couple means reducing dependencies. We all know that the more interactions between objects, the more complex the software will be, so reducing the dependencies means making the software simpler.
- Set Rules and Constraints
  Design patterns basically is describing the rules of the relationship between objects in a specific context. To make software reusable, stable and manageable, we do not allow objects interact each other randomly, they have to follow certain rules. This is quite similar in human society, we have to maintain the orders via laws, rules or regulations. 
Encapsulate changes
   One of the advantage of design patterns is how it deals with change: encapsulate changes. Which means when we identify a concept which it changes, then we encapsulate it by putting it into a class.  we don't want them randomly change. we put them in a box, isolate them. Once we put those details evil in the box, then we can understand or control the system by using abstraction. Then the system becomes stable, manageable and controllable

Conclusion
  • In General software belongs to complex domain. The agile practices are the right practices to solve the complex domain problems;
  • Writing clean code will help us reduce the complexity, will move from complex to simple/complicated domain;
  • Writing messy code will increase the complexity, will move from complex into chaotic domain, this is what we are trying to avoid.
Strategy
So our strategy will be constantly refactoring our code base, keep code clean, avoid messy code.

Resources

Saturday, December 3, 2011

How javascript call java in Phonegap android


Phonegap is a great mobile solution, since I am working in Grapple mobile now, our platform use quite similar solution with Phonegap, so I really want to learn Phonegap to see if we can steal some ideas from it.
What troubled me a long time is in its android platform: I wonder how does its javascript code calls java native code? Before I tried to read its android source code, but did not find the answer. This week I spent some time on its source code, finally I find the answer. I would like to share this result with you, this might be valuable especially if you want to dig more to phonegap, since I seldom find the answer from google or books about phonegaps, none of them talks about this.

The phonegap source code I checked out is from github, the current version is 1.2:
1. phonegap android source code: https://github.com/callback/callback-android
2. phonegap platform sample code: https://github.com/callback/phonegap

Digging the source code
From phonegap-1.2.0.js

For example looking at accelerometer:  in javascript layer, the accelerometer is implemented by calling Phonegap.exec() method:
The PhoneGap.exec() method will be like this: So the exec method will invoke a javascript prompt()- which is popping up an dialog, huh, it sounds weird.

Let's look at the java code:
Inside com.phonegap.DroidGap.java, find the inner class GapClient, which is a subclass of WebChromeClient, it override the following 3 methods: onJsAlert(), onJsConfirm() and onJsPrompt()
Here we only look at the onJsPrompt(), look at the android API for onJsPrompt():
Tell the client to display a prompt dialog to the user. If the client returns true, WebView will assume that the client will handle the prompt dialog and call the appropriate JsPromptResult method. If the client returns false, a default value of false will be returned to to javascript. The default behavior is to return false.

So it is quite clear that: if prompt() is called in javascript layer, then onJsPrompt() method will get invoked in java layer. Phonegap just uses this way to handle the javascript to java communication.

Let's look at the onJsPrompt() method in details:  So here the phoneGap PluginManager will delegate the the javascript call to different native plugins.

From the article of http://stackoverflow.com/questions/7251557/phonegap-and-prompt
and phonegap release note: http://phonegap.com/2011/04/28/phonegap-0-9-5-released/, it mentioned that
Worked around JavaScript bridge exception for Android 2.3. Use “prompt” instead of calling objects directly.
So it seems that this is a workaround for an issue in Android 2.3.

Summary
To recap, this is the flow of javascript call java in phonegap android is like this:
1. in javascript layer, all the javascript method will finally delegate to Phonegap.exec() method
2. PhoneGap.exec() will call prompt()
3. In java layer, DriodGap.GapClient override onJsPrompt(), which will capture the prompt() method call in java, which then delegate to PluginManager to invoke the native java method call.


Friday, November 25, 2011

3 types of work - yesterday, today and tomorrow

I found it is useful to describe software developer's daily job into 3 different types: yesterday, today and tomorrow.
Yesterday: bug fix, maintenance job. since this kind of job is based on the product which is supposed to be finished, so I describe it as yesterday.
Today: developing phase, the work on the product is under development,
Tomorrow: some research and R&D work.
These 3 different type has different nature, and they need different mindset and strategy to deal with them.
Let me dig them into deeper.

Yesterday's work
Yesterday's work are bug fixing and maintenance job. This kind of job is putting off fire, they are urgent, and undeniable. We need to fix them ASAP.

Yesterday's work has no value or negative value, because customer already paid us up front, this work is support and service. This kind of job is not adding value, but removing the negative value.
The more time and effort we spend on the yesterday's work, the less value remained for us. The cost of fixing a bug in production phase is much expensive than fixing it in developing phase( today's work).

Yesterday's work is quite stressful. A minor issue delayed in yesterday will cause higher priority work. Yesterday's job is quite critical for time. we just need the job get done, there is no time for refactoring, no time to focus on better design. There is no room for developer to improve the system (code base, design, code quality etc) at this stage.

If there are too many yesterday's work, then this is not a good signal: It means we have a large amount of technical debts from today's work, it means bad design and careless decision.
So yesterday's job is highly dependent on today's work.
Ideally we should keep the number of yesterday's work as low as possible.

Today's work
Today's work is about current realistic issues. Today's work is the tasks which is belong to developing phase. We develop a new feature which is our customer wanted, so this job will bring values. They are urgent and important, but some features can be negotiable. Customer will focus on feature than time, so the time is not so critical as Yesterday's work.
Developer has lots of room to improve the system, he can have time to improve the design, refactoring.

The strategy of today's work will be - Build quality in. Focus on quality over time. If we focus on quality at this phase, then time must be shorten on maintain phase.
Quality means more than functionality, also means maintainability and readability.  We should focus on simple design, write clean code, keep refactoring. and do not easily leak the bug to maintenance phase.

Tomorrow's work
Tomorrow's work is focused on research and innovation. It will bring us potential value in future, so I call it tomorrow's work, means work for tomorrow.

It for a long term goal, we might not realize its value at present. it's important but not so urgent.

Tomorrow's job is like investment. there is a risk, we don't know how much value it will bring us.

Usually the priority of tomorrow's work is less than yesterday and today, if there are too many work spending on yesterday and today, then there is no time for us on investment. But if we did a good job on today's work, then we need less time on yesterday, then we have more time spending on tomorrow.

Mapping to First thing first
I found these 3 types of work map perfectly with Stephen Covey's first thing first :
Yesterday - Urgent but not important
today - Urgent and important
tomorrow - Not urgent but important

Conclusion
Yesterday is your debt, today is your earning, tomorrow is your investment.
We need to focus on today's work, keep improving the quality of today's work.
If we want to be productive, we need to balance these 3 types of work wisely.