Thursday, June 6, 2019

Day 2 : Diaries from Summer Vacation 2019

We took an awesome and memorable 10 day road trip (17th May 2019 - 27th May 2019) from Chandigarh to Amritsar via Himachal Pradesh. These are the notes taken every night from that vacation. I will publish them one day at a time for the next 10 days. 

18th May 2019 Day 2 : 

The hotel we stayed over last night had a huge window and it opened towards a government school. As I was mentioned yesterday the infrastructure at Chandigarh is amazing. Here is a picture of that school. 



I haven't seen such open spaces   in some of the privately funded schools of Bangalore, which charge a high fee. The first and the only planned city of India is something to be proud of and needs to be emulated across. 

The objective for today was to visit Rock Garden and then reach Mandi before sunset. That would have given us ample rest before we drive to Kulu via Prashar Lake. After breakfast we landed in Rock Garden and it is one of the most amazing places we have seen in India. It was very clean and has amazing collection of things made from rocks. It is one man's creation (Nek Chand) and I can only imagine what would have happened to him had he not found some support from a city like Chandigarh. The garden is world class. It could be a bit more well maintained (the signs and audio guides are missing.) And has the potential of becoming a much more popular tourist spot. 
After rock garden, we decided against visiting the lake in Chandigarh and drove towards Kirtarpur Sahib. Pradeep (our zoomcar ground executive) had suggested that if we drive towards Mandi then that's the city from which we should cross over to Himachal, as we would easily spot the RTO office of Himachal where we will have to pay the road tax.
On the way to Kirtarpur Sahib it was almost time for lunch. We did Google around a bit and figured that there are a lot of Gurudwaras in Anandpur Sahib. It adds a bit of drive for us but then we can see a nice Gurudwara, have Prasad in Langar. We also saw that there is a highly reviewed and rated museum called Virasat-e-Khalsa. We visited Gurudwara Kila Sri Anandgarh Sahib and had our lunch over in langar. Post that we visited Virasat-e-Khalsa which is an amazing museum. The entry is free and the structure is clean and has an imposing presence. The exhibits inside were very well maintained and planned. We ended up spending a good amount of time in these 2 places. And that meant we were going to be driving late. 

We started from this place around 4.15 PM and the question in our head was, do we want to visit Bhakra dam as it could be a life time experience. We decided against it as it would have added a couple of hours of drive time and another hour of visiting time.We wouldn't have made there during the sunny hours and visit would have been out of question.
We started to drive towards Mandi. On the way we had dinner around 7 pm. It was good chapati (got them after 2 days as all we got in Chandigarh was tandoori rotis) with dal and Potatoes. 
We kept driving and finally halted for night in a Oyo around 10 kms before Mandi. 

We want to visit Prashar Lake and land in Kulu by sunset tomorrow. Let's see how it pans out. 

Signing off day 2

Day 1 : Diaries from Summer Vacation 2019

We took an awesome and memorable 10 day road trip (17th May 2019 - 27th May 2019) from Chandigarh to Amritsar via Himachal Pradesh. These are the notes taken every night from that vacation. I will publish them one day at a time for the next 10 days. 

17th May 2019 Day 1 : 

This is our second summer vacation with Reyansh. Last year we had gone to Singapore however this year we decided to keep it within India. Whilst planning this vacation all we could agree on was that we land on Chandigarh and take off from Amritsar. We could never agree or deliberate on what to do for the days in between. 
As we kept postponing to plan the plan, the date to take off came very near, and so we decided to make the best use of this unplanned trip. We decided to make it an impromptu road trip where we will decide the night halt and next days plan on the go. 
Here starts the day 1 of this trip.  
We took a cab from our home to Bangalore airport. The cab was booked through MakeMyTrip and the cost of Rs. 789 is a steal for us. Halfway through we realised that Reyansh is feeling sick. Is it due to motion sickness ?(happened in our last trip to Yercaud and Maheshwar) or is it because of some bad food he had ? We still don't have the answer. But we are worried as we do have a rough idea that we will go to Himachal on between Chandigarh and Amritsar. We have approximately 10 days!!!.
As we reached airport, the flight or Chandigarh is a non stop air Asia flight. Reyansh slept for an hour in between while me and Richa couldn't. The funny part was that Reyansh had a couple of glasses of water before he went to sleep, he got up as the cabin was being prepared for touchdown. As soon he got up he wanted to pee and cabin crew refused to allow us to leave seats due to turbulence and aircraft was preparing to land. This is the first time he could control his urge to pee, successfully for 15 mins, and he went to restroom as soon as we landed. I was prepared mentally, to clean up the seats after he wets his pants but it never came to it :). 
After we landed in Chandigarh we took a cab to pick our rental car from Chandigarh railway station. We had booked a Ford EcoSport as it's a new model and were looking forward to take it for our trip. However as soon as we landed in Chandigarh , Zoomcar executives called us to inform that they don't have the EcoSport available as it needs some maintenance and they can offer a scorpio or a swift hatchback. We chose scorpio as it sounded like an upgrade. However once we reached the pickup site we realised it was an old scorpio which was already driven for more then 85000 kms and the driving experience was not the best. As we prepared to accept our fate, Richa saw an EcoSport and asked the onsite Zoomcar executive as to why we aren't offered that as we had booked an EcoSport. The exec on ground asked us to call the call centre. When we called them they couldn't offer it as it was booked by 3-4  people in next 7 days and they didn't want to apologise to all of them. I asked them if they could offer something else, I can also see some XUVs there . Finally they offered us with XUV W5 version. It had closed 908 kms before we took it. 
It was a good upgrade for us. 

We then drove to international dolls museum which was established in 1985. The museum has dolls which look like brides from various states in India, they also have dolls which represent culture of different countries. However the museum needs upkeep and a way to make the tour interesting. The souvenir shop didn't have any dolls on offer, which is surprising.
Next we went to Zakir Hussain Rose Garden which is spread over 40 acres and has almost 800+ variety of roses. The roses weren't blooming but Reyansh enjoyed running in open spaces. 
In the evening we roamed around in the city and had dinner at a pure veg restaurant (Sindhi Sweets) in sector 17. The food was good and Richa also did some shopping . 
I loved Chandigarh city, it's planned and can compete with any city in the world in terms of infrastructure. Can't understand why we can't simply copy the best practices from a city like this and make whole of India like this. 
With this ...signing off from day 1. Tomorrow we go and sleep in Mandi . And need to visit Rock garden before we leave ....
Signing off day 1.

Wednesday, March 27, 2019

Connecting to Cloud Foundry Kafka Service from your localhost using Kafkacat

So we are developing a cloud foundry application  and one of the backing services we use is a Kafka Service. Our backing service uses SASL for authentication and uses a self signed certificate issued by the owner of the backing service.

Now we all know that while deploying and debugging  the application on localhost while connecting with Cloudfoundry backing is sometimes a necessary evil and depending on your network setup it could sometimes be tricky.

I managed to make Kafkacat (https://github.com/edenhill/kafkacat) connect to the backing service from my local macbook. Here is how you can achieve it.

Here is how my service looked like in the VCAP_SERVICES variable.


Now there are a couple of challenges for me to work with service using Kafkacat.

  • The username and password given in the VCAP_SERVICES variable don't work directly with Kafkacat. We have to generate a Token using the token services URL given in the json and then provide that authentication token as password to the utility. 
  • The broker IPs and the zookeeper IPs (10.254 series of IPs in the json) are unreachable from my local machine.
  • The SSL communication between kafkacat and kafka service is encrypted by a certificate which is issued by the rootCA which is available on  https://kafka-service-broker.example.com/certs/rootCA.crt

Let's solve these issues one by one. 
  1. In order to create the token to be provided to the kafka service as a password you can use the following script. The envrionment variables USERNAME and PASSWORD are set to the values which you found in the VCAP_SERVICES. The output of this command can be set in another environment variable TOKEN which we will use in the final steps.    
  2. You should store all the BROKERS in an environment variable called BROKERS. 
  3. In order to make the kafkacat work, we need to make sure that we are able to reach the 3 broker IPs given in the environment variables from the localhost. We will do this with the help of virtual interfaces and ssh tunnels on the macbook. I didn't manage to find the right way to do it using bash so I am listing down the steps you need to take from UI (with screenshots). 
    • Open the network option in your System Preferences and from the bottom wheel select "Manage Virtual Interfaces" .  
    • In the next dialog select Add VLAN option to add a VLAN. 
    • Give the VLAN the name vlan0 and select an interface. (You need to select the interface you are connected to else it doesn't work). 
    • Press create->done and ensure that VLAN appears in the network dialog, as shown below. 
    • Now go ahead and change the Configure IPv4 from DHCP to manually and assign one of the IP address which we had in the VCAP_SERVICES to this vlan interface. 
    • After this go ahead and duplicate vlan0 2 times. The option is available as shown below. 
    • Make sure that you enter the other 2 IPs in the duplicated interfaces. After this step my dialog looks like the following. Please note that IP is different for all 3 interfaces. For me vlan0 => 10.254.33.21, vlan1 => 10.254.33.22, vlan2 => 10.254.33.23 now. 
  4. After the above step, the macbook now starts responding to all the 3 broker IPs. Now we need to ensure that any request on these interfaces is tunneled to the real Kafka brokers hosted in Cloud Foundry. To do that I establish 3 SSH tunnels with the commands below. 
  5. In order to provide the rootCA.crt to kafkacat, I download the certificate to the local machine in a folder from where I intend to use kafkacat. I use curl  to do this. 
  6. You can install kafkacat on mac using brew
  7. Now you can start using kafkacat with its normal commands, however since it's a SASL setup, you need to provide some parameters to make it work. Here is how I use kafkacat to list all topics.  You can use the same format to execute any other kafkacat commands you are interested in. You can also use your java application running your localhost to now start connecting to the remote kafka service on cloudfoundry. 

Happy coding
!Abhishek

Monday, March 11, 2019

Ubuntu with a desktop and RDP on Azure

Often while working on various projects, we need VMs with the OS which is different then the one available on local laptop. 
More often then not I need Ubuntu which I don't have on my mac and I end up creating a VM on Azure, RDP into it from my local mac machine. 

In order to do this, one can create a VM on Azure (I chose Ubuntu 18.04 LTS image on Azure). Once created SSH into machine and follow the below instructions to ensure that you are able to RDP into this machine. 

Use the following script to achieve it. 

You can now go ahead and RDP into the machine. 

Tuesday, February 26, 2019

Deploy your own UAA in Cloudfoundry

One of the interesting backing service in the cloudfoundry landscape is a UAA. In most cloudfoundry editions (e.g. Pivotal or SAP and probably in others too) one gets UAA as a backing service. However from time to time one wants to run their own UAA to see how things are really working or just for the high of having their own UAA :). 
Recently I had a requirement to host a UAA of my own as I was trying to understand how the JWTs are really getting issued by UAA and how exactly are they signed etc. 
As I turned to web to ensure that I can host my own UAA, it turned out that most articles do not have enough instructions to host a UAA in PCF as an app. Thus came the idea to document all I had to do to deploy my own UAA. 
Note that below instructions can be followed to get a just about working UAA and are in no way enough to install the UAA for production purposes. 

Here are the basic tools you would need to finish this exercise.I have a mac so most commands assume at least bash

1) git CLI
2) uaac (gem install cf-uaac) 
3) cf cli with access to a CF space where you can deploy an application 


Once you are set with these command line utilities, here are the steps to follow 

1) Go ahead and clone the repository https://github.com/cloudfoundry/uaa.git 
2) once cloned you need to make a few changes in some files. 

In the file uaa/src/main/resources/uaa.yml go ahead and add the following lines in the begining of the file 


Next go ahead and uncomment the section jwt and cors in the same file. It looks like the following 

Then go ahead and open the file uaa/src/main.webapp/WEB0INF/spring/saml-idp.xml and add a keyManager for the bean idpMetadataManager. After this addition the bean definition looks like 


Lastly we need to change the memory and timeout for the deployment descriptor found in uaa/src/test/resources/sample-manifests/uaa-cf-application.yml 


3) Once these changes are done go ahead, build and deploy the application using the following commands 

4) Now that you have deployed the UAA. It's time to login to the UAA using uaac

You can probably change this secret in /uaa/src/main/webapp/WEB-INF/spring/oauth-clients.xml (I haven't tried this bit though) 

5) You can even create a new client credential on UAA by using the commands below. You can use these commands to list the JWTs issued by UAA as well. 

Happy Coding :) 

~Abhishek

Monday, August 21, 2017

SCI and User, Roles and Groups

In the previous post I discussed how to get started with SAP ID Service and build a simple HCP Application which outsources its authentication to SAP ID Service. 
Now let's extend this scenario. In general I like to use Identity Provider to provide me with user attributes like name, email address etc. and also provide me with group memberships. So the greeting service should greet the end user with the real name, rather then an ID like P0000 which we saw in the previous post. 

I would also like to introduce 2 roles in my application viz. Everyone and GreetingEditor. 

At the application side I generally prefer to create roles and groups. These roles and groups on the application side have a 1:1 mapping. So we will create a group called GreetingEditor and a group called GreetingEditors.

While creating/enrolling the application with the IdP I generally like to map the groups on IdP side with the groups on Application side. These mappings could be based on AND or OR condition. e.g. A user in IDP who is present in both 'ChiefGreeters' and 'Editors' group should be mapped to the group called "GreetingEditors" in my greeting application. 

The group GreetingEditors should then be assigned the role GroupEditor. 

Let's extend our Greetings Application for the above scenario. Let's first fix the fact that it greets the end user with her name rather then the crazy ID like P0000. 

Open web.xml and add the following entry 




Then open your Greeting.java and in your doGet method add the following code. 


What you are essentiallly doing is that you are using User Provider available in HCP to parse and provide us with the SAML attributes which we get from the SAP Identity Service. In order to ensure that these attributes viz. firstname and lastname are available with the application we need to configure the application correctly in the SAP Identity Service management console. 

Go to your Management Console and choose Applications & Resources -> Applications -> Custome Applications -> sayHello (This is the name of my applications" -> Assertion Attributes.
Now Ensure that you have First Name and Last Name added in the user attributes. This is how the screen should look like 




If you look at the screenshot above the attributes are called first_name and last_name while I query firstName and lastName in my application code. This is because the second mapping is yet to be done. In the second mapping we are going to map these attributes for the application in the Cloud Cockpit. Go to your SubAccount -> Trust -> Application Identity Provider -> (Select the IdP) 

Now select Attributes tab and add 2 assertion based attributes. The assertion based attribute should map first_name to firstName and last_name to lastName. This is how my screen looks like 




This mapping ensures that the SAML attributes coming from IdP are mapped to the user attributes in the application which is using the UserProvider. 

Now deploy the application and run it. It should now say "Hello, <>" 

So we achieved the first objective of this exercise. As a matter of fact you can map many user fields like phone number, address, groups etc. as assertion attributes in the Application Configuration at the IdP side and then map them to custom attributes on the IdP configuration at the application side. 
This helps us with the fact that you can outsource the user management totally to SAP Identity Service. 

Let's go ahead and now and configure the roles and groups as per our requirement. 

First let's try to setup roles to ensure that we have OOB roles created when we deploy the applications. 

Open web.xml and add the following security roles there. 





Please note that the role EveryOne is created and assigned to every authenticated user by default, so you need not specify this role in the web.xml. Next time you publish your application to HCP you'd see a role called GreetingEditor. In your cloud cockput, you can go to SubAccount -> (Select the Application) -> Security -> Roles.  



Once this is done let's go ahead and create a group called GreetingEditors. On the same screen click Assign on the Groups tab and create a new group and save it. Once it is assigned to the role this is how your screen would look like. 



Now let's go ahead and add the relevant groups we discussed to the IdP. In the SAP Identity Service admin console go to Users & Authorizations -> User Groups and Add 2 new groups. Now go to the User Management and assign these 2 groups to a user. This is how my user looks like after the changes are done. 




Now we need to ensure that these groups are sent to the application as part of SAML attributes. In order to do this we need to go to Application Configuration on the IdP side and add another SAML Assertion Attribute called groups to the list of attributes the IdP passes to the application. Here's how my screen looks like once I make this change. 




Once this is done we need to ensure that we do the appropriate mapping in the application such that if a user is part of both ChiefGreetors and Editors group in IdP, she is assigned to GreetingEditors group in the application, thus assigning her with the role GreetingEditor.  In order to do this we need to enter the IdP configuration in the HCP Cockpit and add a simple assertion based group in the Groups Tab.  Here's how my tab looks like after the change. 



Now let's  change the doGet method of our greeting service to list out the roles the logged on user has been enrolled in. Change the doGet method to the following. 



Try running your service with the user who has been added to both ChiefGreeters and Editors group and you should see the output which looks like the following. 



Happy Coding!!

Monday, July 24, 2017

Getting Started with SAP Identity Service and HCP Cloud

So I recently started working on Hana Cloud Platform and one of the first challenges which await me is to figure out how to achieve SSO in a set of simple applications my team is writing on Hana Cloud Platform. 
Since we are working on Hana Cloud Platform, choosing ID Service is easy, it has got to be SAP Cloud Identity Service. Here are the steps you need to follow, to get you started on HANA Cloud Platform with SCI Service. 

Objective : At the end of this blog you should be able to 
  • Run a simple greeting service which would greet the logged in user using SAP Cloud SDK on your local machine
  • Deploy the greeting service on cloud and configure the application and SCI tenant to greet the end user. 
Pre requisites : In order to make the scenario work, you need a HCP account and access to a tenant of SCI service. You may want to work with your SAP contact to get a handle to both of them. You can also request for the trials online.  Once you have access to both, please ensure that you have setup your eclipse with SAP Cloud SDKs. You can follow the instructions on this link to setup your development environments. 


Let's get started. 
  1. Fire up your eclipse and create a new Dynamic Web Project. Here are a few things to set while you create it 
    • Name : sayHello
    • Target Runtime : SAP -> Java Web Tomcat 8 . It may ask you to set path to a Neo SDK. I set it to the folder where I have unzipped neo-java-web-sdk-3.30.16 SDK. I chose the default workbench JRE which is a SAP JVM in my case. 
    • Dynamic Web Module Version -> 3.1 
    • I set my sources folder on build path to /src/main and Default output folder to build/target
    • I do check the Generate web.xml deployment descriptor to true in the wizard. 
  2. Now let's create a new Servlet. Here's what I fill in my wizard
    • Java Package : com.sample.helloworld
    • Class name : Greeting
    • URL mapping : /greeting
  3. Add the following code to the doGet and fix the imports
  4. Right click the project -> Run As -> Run on Server. 
  5. You now need to define a local tomcat server. Choose SAP-> Java Web Tomcat 8 Server and finish the wizard. 
  6. Now try opening http://localhost:8080/sayHello/greeting and it should throw up a login screen. We can't login yet since we haven't defined a user in the container yet. Let's do that in the next step. 
  7. Double click the newly defined server in the Servers window of your eclipse. Open Users tab and add a new User. I choose my user name as test. 
  8. Hit the service http://localhost:8080/sayHello/greeting again and login with the newly defined username and password. You should now see an output "Hello, test" in your browser. 
Now that we have a locally authenticated service working in our eclipse, let's publish the application to HCP and outsource our authentication to SCI. Here are the steps to do that 
  1. Right click on Servers window of your eclipse and choose New Server. 
  2. In the dialog box which shows up choose SAP-> SAP Cloud Platform. Enter the correct region code for your HCP account. You can find the available regions and hosts here. Mine happens to be int.sap.hana.ondemand.com. (If host for your region is not available on the page, check the post here , as it may help you figure out your host. SAP uses some conventions so you may crack it yourself. )
  3. Enter the application name as sayhello, You can leave the runtime to be chosen Automatically. 
  4. The subaccount name is available in your Hana Cloud Cockpit. Enter the subaccount and your credentials. 
  5. Add the sayHello application to the configured resources for the server, and press Finish.
  6. It will take some time, but finally the application should be deployed successfully, Copy your application URL from the Server window and hit the greeting service using a browser. The URL for my service was https://sayhelloi031884sapdev.int.sap.hana.ondemand.com/sayHello/greeting and the error I got was "Identity Provider could not process the authentication request received. Delete your browser cache and stored cookies, and restart your browser. If you still experience issues after doing this, please contact your administrator." The error is unintuitive and should have been something different like "There is no IDP configured for this application so I can't allow you to login" 
The application is now deployed successfully on HCP so let's proceed to configure the SCI for this application, 
  1. Open your HCP cockpit and navigate to the subaccount in which you deployed the sayHello application.
  2. On the left hand side navigation choose Security->Trust and click 
  3. Change the Local Service Provider from default to Custom, Click Generate Key Pair to generate a new key pair. Let Principal propogation and force authentication be Disabled. and save. 
  4. Select the next tab i.e. Application Identity Provider and click Add Trusted Identity Provider. 
  5. Before you proceed any further you need to open the SCI tenant in a new browser tab which you have. I have mine hosted on https://i031884.accounts400.ondemand.com/admin/ . Logon to this tenant as administrator and go to Tenant Settings -> SAML 2.0 Configuration and select to download metadata file. 
  6. Go back to HCP console ( i.e. the browser tab you were using in step 4 to add trusted identity provider) . Browse and select the metadata file we downloaded in step 5. Choose Save.  i031884.accounts400.ondemand.com should now be your default identity provider. 
  7. Go to tab Local Service Provider and click Get Metadata again.  Save the file in downloads folder 
  8. Go back to SCI tenant (Browser tab which we opened in step 5) and navigate to Applications and Resources -> Applications. 
  9. Click Add Application and give a name sayhello and click save
  10. select sayhello application and click on SAML 2.0 configuration. Browse to the file you saved in step 7 and click save. You have now configured the application and IDP to trust and know each other. 
  11. Try hitting the application again (https://sayhelloi031884sapdev.int.sap.hana.ondemand.com/sayHello/greeting in my case) and it should prompt you to enter id, password and you are good to go :).

Happy coding!!!!