Jim Hagemann Snabe, former SAP co-CEO and now SAP alumnus, shares insights about the future of work and has four personal messages for employees.

Jim Hagemann Snabe – I’ve spent time on five different boards, including SAP’s of course. This year, I was asked to be the chairman of board of A. P. Moller Maersk, the largest container shipping and logistics company in the world. In January next year, I’m nominated to take over as supervisory board chairman of Siemens, one of the world’s largest industrial conglomerates. On top of that, I’ve kept my role at Allianz, where I’m now a vice chairman.

what could SAP’s contribution be to them?

In manufacturing, the assumption so far was that companies relied on mass production in low-cost locations. I think we’re now moving production back closer to the customer. Instead of mass-producing, companies will be producing individual items and, as such, delivering more accurately on individual customers’ needs. I actually believe that we have an opportunity now to rethink the value chain and move toward more circular economy concepts where we don’t consume resources, but use them and give them back ‒ for a much more sustainable future.

I believe that we now probably have the biggest opportunity ever in terms of creating a society that is significantly better than the one we have today. We can create or reinvent entire value chains for something that’s better, more individual, and much more sustainable. The challenge will be the transformation itself. How do you get there? It’s a very big change, so it will dramatically change the way we do things: It will challenge existing jobs and create new ones. So major reskilling will be necessary.

I believe the winners will be the companies that master the physical and the digital worlds in parallel. And a lot of the work I do in my board roles is to help accelerate the digital dimension in physical companies like Siemens and A. P. Moller Maersk, so they can master both in parallel.


What is your message to SAP employees?

Jim: First of all, I miss everyone at SAP. Secondly, I would send a big thanks to Bill McDermott for being such a great partner, leader and friend. SAP is a very special company with not just a big brain, but also a big heart and very capable hands. I would urge everyone to be extremely proud of what you’ve achieved and of the special DNA that the company has. Keep that!

At the same time, my message would be: Be ambitious and challenge assumptions! Because you can’t succeed in the future by looking back at historic successes. You have to keep challenging your assumptions so that you always stay relevant and ahead of the game. SAP has proven its ability to reinvent itself from a position of strength. Keep doing that, at an even higher pace in the future.

My third message would be: Make sure you develop the capabilities that matter the most! Which is really about unleashing human potential and allowing experiments, while increasing efficiency at the same time. Being ambitious on efficiency unleashes the capacity and investment opportunity for the experiments, and it’s the experiments that will create the future. But you have to make sure those two elements go hand in hand.

My last point is: Never forget the customer! The companies that fail to reinvent themselves from a position of strength are those who get obsessed with themselves. I believe that SAP has always been about the customer, and if we keep that in mind, the company has the potential to be extremely successful in the future.


SAP clearly plays a very important role in the world. That’s a reason to be proud, but it also carries enormous obligations.


By Andrea Diederichs

(Just copy from SAP and using it for my-self, do not use this if do not ask)

Benchmark – Node.js vs Java

by benchmark task performance

sourcesecsmemgzcpucpu load
Node.js4.02507,4804524.020% 1% 100% 0%
Java12.16927,21292937.2873% 81% 75% 78%
sourcesecsmemgzcpucpu load
Node.js27.8228,208129727.811% 0% 1% 100%
Java21.5027,240148921.521% 1% 100% 0%
sourcesecsmemgzcpucpu load
Node.js17.49564,70477862.7784% 84% 96% 97%
Java5.8989,50479623.0898% 98% 98% 99%
sourcesecsmemgzcpucpu load
Node.js3.68245,49610883.934% 4% 98% 2%
Java1.11345,30816612.4433% 58% 54% 80%
sourcesecsmemgzcpucpu load
Node.js15.7728,80442515.771% 0% 1% 100%
Java4.2931,42895016.5697% 96% 98% 97%
sourcesecsmemgzcpucpu load
Node.js9.4531,89217459.461% 1% 1% 100%
Java2.1436,19224575.6871% 58% 62% 77%
sourcesecsmemgzcpucpu load
Node.js78.4127,19247378.391% 1% 100% 1%
Java17.7430,048128269.9098% 98% 100% 99%
sourcesecsmemgzcpucpu load
Node.js50.22927,54044051.076% 15% 77% 6%
Java11.33592,66883539.3984% 92% 83% 91%
sourcesecsmemgzcpucpu load
Node.js60.732,095,052904151.7496% 84% 84% 83%
Java8.02467,004180225.5776% 98% 73% 74%
sourcesecsmemgzcpucpu load
Node.jsBad Output
Java0.248289380.2471% 38% 8% 4%
Javajava version “1.8.0_121”
Java(TM) SE Runtime Environment (build 1.8.0_121-b13)
Java HotSpot(TM) 64-Bit Server VM (build 25.121-b13, mixed mode)

Using Swagger to define API RESTful endpoints

It then generates API Documents and Application Skeletons for you. Afterward, you can write code to implement the APIs’ functionality. Another similar tool is RAML.

I personally think that if you are using Ruby, you can just write a good README file about APIs, and done with it. It will be much faster and  cleaner, if you know what you are doing. However, if you run a project that build multiple services by different teams with different skill levels, things such as Swagger and RAML will help you to maintain a certain level of unification of different codebases. And those tools also help to keep the APIs in synch with API docs (Lazy developers will like this feature).

This article describes step-by-step  of using Swagger to define API functions, generate a Sinatra skeleton web-based app and write code to implement the app. The Sinatra skeleton generated by Swagger does not work out of the box, and the quality of Ruby code is terrible, so I have to do some modifications myself to make it work and be bearable.

The steps are:

  • Write YML file that contains API definitions.
  • Generate and download the Sinatra skeleton.
  • Modify the code to make it work.
  • Implement the APIs’ functionality.
  • View API documentation and test the functionality from Web browser.

I. Prerequisites

There are Swagger tools that you can download and use offline on your computer. To me, they are not attractive, so you can see about downloading and installing them here.

But to use online tools, you just need a web browser. I test the tools with Chrome and Opera on Mac OS X, and they work.


II. Write YML file that contains API definitions

Use your web browser to go to the Swagger YML Editor:  http://editor.swagger.io/#/

On the browser, you will see this screen if you come to Swagger Editor the first time:


Click on the button “Got it!”, you will come to a screen to edit the YML file that describe your APIs. In the editor on the left side, you will see the YML definition of the example app Uber API like this:
You can delete everything in the YML editor on the left, and write your own API definitions there. I already wrote the YML definitions for two APIs of Email Services in this YML file.

POST /verifications.json

When a user registers a new account on a site, developer can use this API to send verification email to user’s email address. User must click on the comeback_url to come back to the site to prove that his email is valid.


POST /invitations.json

When a user or an organization invites a user to participate a site, developer can use this API to send the invitee an invitation email. The invitee can click on the invitation email to come to the site.


Both API endpoints accept JSON parameter with this format:

“organization_name”: “Some Organization Name”,
“recipient”: “somebody@some-email.com“,
“comeback_url”: “Some full URL, including protocol http/https”


For example:

“organization_name”: “Amazon”,
“recipient”: “somebody@rubygems.org“,
“comeback_url”: “http://rubygems.org

You can read details about YML and JSON specs for API definitions here: http://swagger.io/specification/ .

It is always easier, faster and cleaner to use YML to define APIs.


III. Generate and download the Sinatra skeleton

For now, you can copy this YML file written by me, and paste it into the YML editor on the left side of the screen on browser, you should see the screen like this:



After you copy/paste the YML file in the YML editor and verify on the right side to see the APIs verifications and invitations get defined correctly, you can download the Sinatra Server skeleton by clicking on the menu Generate Server, and select Sinatra.

A zip file called sinatra-server-generated.zip will be downloaded to your local machine. Extract the file, you will have a directory called sinatra-server. That is your Sinatra Server skeleton generated by Swagger. Feel free to change the directory name to any name you want.


 IV. Modify the code to make it work

The generated Sinatra skeleton has some troubles, so it does not show APIs or anything out-of-the-box as it supposes to do. Besides, the Ruby code quality generated by Swagger is terrible. So we need to do some modifications to make it work.

1) my_app.rb

Add require to include the files in ./api/, so the application will know about the API endpoints’ definitions.

2) lib/swaggering.rb

– Method self.add_route:

The line “accepted = case method” never works, because the method names in APIs are generated as UPPERCASE, while the accepted tests for the method names uses lowercase.

And the way the code is written to check for valid method names are super dumb. Please look at the modified file for a much better and cleaner implementation.


– Method self.to_api:

This method hardcodes base_path in api_listing to the one in @@configuation. It makes the API docs stop working if the application is deployed to any place other than “http://localhost:4567”.

Please look at the modified file for a much better and cleaner implementation.

3) Two files invitations_api.rb and verifications_api.rb

The two API endpoints are defined in these two files.

The API definitions, routes, resourcePaths and endpoints must be modified to reflect (to some degree) the correct APIs defined in the YML Editor (See the right side).
Please look at the modified files invitations_api.rb and  verifications_api.rb, at the parameters of MyApp.add_route.


After the 3 steps above, you should be able to fire up the server using the command rackup -p 4567 config.ru.

Then  you can use any REST client, for example Postman to test the APIs at:

POST http://localhost:4567/invitations.json

POST http://localhost:4567/varifications.json

In both cases, you should receive back a JSON:

{“message”: “yes, it worked”}

Now we can start to implement the functionality for the email APIs.


V. Implement the APIs’ functionality

I implement the Mail functionality using the gem ActionMailer.

Everything follows the Rails conventions: the mailers are in ./app/mailers/. The mails’ contents are in ./app/views/.

Take a look at the repository for implementation details.

You must configure the email sending configuration in the file ./config/initalizers/setup_email.rb to be able to send mail.

If you run the application on any OS that has postfix, you can configure the file ./config/initializers/setup_email.rb like this:

ActionMailer::Base.raise_delivery_errors = true
ActionMailer::Base.delivery_method = :sendmail
ActionMailer::Base.view_paths = File.join(‘./app’, ‘views’)


VI. View API documentation and test the functionality from Web browser

I add the directory public with modified Swagger UI to the application, and add two new routes in the file my_app.rb to support the API docs functionality. It allows users to view API docs, regardless where the application is deployed.

Once you finish all the modifications and APIs’ implementations, run the server with the command rackup -p 4567 config.ru, then you can see the API docs by open this URL in browser:


Replace localhost:4567 with the real URL where you deploy the application. You should see something like this:


You can click on “Show/Hide” and “List Operations” to view details of each API endpoint.



You can try out the APIs by clicking on “Expand Operations“. Once you click on “Expand Operations“, you will see a screen similar to this:


You should be able to paste parameter similar to the following JSON in to the text box Value, and hit “Try it out!” to see the API endpoint run.

organization_name“: “My Awesome Organization”,
recipient“: “somebody@some-email.com“,
comeback_url“: “http://www.google.com”


For your convenient, I put the fully implemented application here: https://github.com/linhchauatl/sinatra-email-services-server

Please read the README file about how to bring it up and running.
Happy swaggering!



Official NASA Software

It is great news that NASA has released an official software catalog 2017-2018 for various technical applications. Time to learn from BIG Brother.

  1. Business Systems and Project Management
  2. Data Servers Processing and Handling
  3. Materials and Processes
  4. System Testing
  5. Propulsion
  6. Electronics and Electrical Power
  7. Operations
  8. Structures and Mechanisms
  9. Environmental Science
  10. Design and Integration Tools
  11. Crew and Life Support
  12. Autonomous Systems
  13. Vehicle Management
  14. Data and Image Processing
  15. Aeronautics


Recap from GS Leadership offsite

HCM – A ‘Cloud Day’

SAP Customer 2017

4 priorities regarding to SuccessFactors:

  • migration from Oracle to Hana,
  • eliminating support issues to improve customer satisfaction,
  • integration within SFSF suite and
  • integration with other SAP products.

putting new codes in SFSF cloud solution today means upgrading 35,000+ schemas for 6,000+ customers in one go. This requires absolute quality focus.


  • ~3K employees (1.5K in San Francisco and 650 are Engineers)
  • ~ 3 million homes (over 2 million booked last New Year’s Eve)
  • Changing their architecture to scale (~100 microservices)
  • They apply Geoffrey Moore’s zone methodology to their work to move past the “innovator’s dilemma”
  • Everyone’s focus is to “drive impact”
  • Engineers are measured against the following expectations: tech ability, productivity, impact, scope, autonomy, influence, and enrichment.
  • Interesting fun fact: When they expanded into Cuba, the country didn’t have online payment infrastructure. Airbnb had to find creative ways to pay the Airbnb hosts (ask one of us for more details about that interesting fact!)
  • As they continue to expand, keeping up with various country legislation is becoming a challenge (and yes, we did mention our tax service J).


Remember 90% Of Everything You Learn


Learning Pyramid

Learning Pyramid

Books, classroom lectures, videos — non-interactive learning methods that results in 80-95% of information going in one ear and leaking out the other.

The point here is that instead of forcing our brains on how to remember more information with “passive” methods, we should focus our time, energy, and resources on “participatory” methods that have proven to deliver more effective results, in less time.

This means that:

  • If you want to learn how to speak a foreign language, you should focus on speaking with native speakers and gain immediate feedback (instead of mobile apps)
  • If you want to get in shape, you should work with a personal fitness trainer (instead of watching Youtube workout videos)
  • If you want to learn a new instrument, hire a local music teacher in your city


UML introduction

UML is a graphical notation specifically for drawing diagrams of an object-oriented system. A UML describes over a dozen different diagrams, but we’re only interested in a few of the most common, such as the classic class diagram.



Class Diagram

Class Diagram

When drawing diagrams, it’s common to see signs before the attributes or methods, most

– Minus signs in front of the attributes here. This is referred to as controlling visibility, and Minus means these should be private to the class, not directly accessible from other objects.

+ For example getName operation which will be public and marked with a Plus sign.



Identifying inheritance


Inheritates Abstract Class

Inheritates AbstractClass

easiest way of identifying an inheritance situation is with two words, “Is A”. Inheritance describes an “Is A” relationship.


Using aggregation and composition

Aggregation Composition

Aggregation Composition

it’s the unfilled diamond. So, for example, we might have a classroom object that will contain an array of student objects that might be important to diagram that relationship.

Document has a Page or has many pages. But if I were to delete the Document object all the associated Page objects should be deleted too. I would not expect then those page objects to be shared with any other part of the application. On the other hand in a plain aggregation situation as with the Classroom and Student relationship, if I deleted the Classroom object, perhaps the class got canceled, I would not expect all the Student objects to be destroyed, they may be used in different classrooms or just be able to live on their own.

And that’s the difference, Composition implies ownership, Aggregation does not. Now Aggregation is not usually worth showing on a diagram, but Composition often can be. If the lifetime of an object is dependent on another object existing that can be worth showing, even if we are just prompting the idea that when you’re defining the owning class, say here the Document class, you may need to write aconstructor and a destructor that would take care of creating and/or deleting the internal objects.


Using interfaces



Sequence Diagrams

Sequence Diagrams

Class Diagram

Class Diagram


Khi một class có sử dụng một instance của class B như một tham số đầu vào của method trong class A.

public class A {

    public void doSomething(B b) {}

Nhưng giả sử class A có một member với kiểu dữ liệu là class B thì lúc đó ta có mối quan hệ



public class A {

    private B _b;

    public void setB(B b) { _b = b; }

Với ví dụ trên ta có thể thấy mối quan hệ giữa A và B chỉ là Aggreation có nghĩa là nếu như A bị hủy thì chưa chắc B đã được hủy. Do vậy nếu như instance của B được khởi tạo trong A như ví dụ dưới đây ta có mối quan hệ là



public class A {

    private B _b = new B();


public class A {

    private B _b;

    public A() {
        _b = new B();
    } // default constructor

Còn mối quan hệ như Inheritance hay Realization thì sao? Đúng như tên gọi của nó, nếu class B kế thừa từ class A ta có mối quan hệ



public class A {


} // class A

public class B extends A {


} // class B

Mặt khác nếu class B implement từ A thì ta có mối quan hệ (Ví dụ ta hay thấy đó là implement một interface)



public interface A {


} // interface A

public class B implements A {


} // class B

OOP: The Specification Pattern


In this article, we are going to explore the classic specification pattern and implement it in order to compose the LINQ queries, and also non-LINQ queries. This article will also help beginners in understanding the specification pattern and how to implement it in practice. Major benefits of the specification patterns include reusability, maintainability, loose coupling of business rules from the business objects, readability and easy testing.

Specification Pattern

Specification pattern as per the definition from Wikipedia, is a particular software design pattern, wherebybusiness rules can be recombined by chaining the business rules together using boolean logic. To put it simply, business rules are segregated based on the Single responsibility principle (SRP) and chained or composed using boolean operands (AND, OR or NOT) to achieve the desired result. Each segregated business rule is called Specification.

Each specification inherits the abstract CompositeSpecification class which defines one abstractmethod called IsSatisfiedBy. This method is the engine of specification pattern. The responsibility of this method is to apply the business rule (specification) on the object in question and return a boolean result. The primary goal of the specification pattern is to select the subset of objects that satisfy a set of specifications chained together.


More infor: