How Scala code gets compiled into Java
For last few days i am learning Scala + play framework. Since i have been using Java for long time now, one that always helps is to convert Scala code into Java Code and see what is going on under the hood. I follow these steps
- First i create a new Scala File say Contact.scala which has one Scala class like this
class Contact{ var firstName ="" private var lastName = "" }
-
Then go to the directory that has Contact.Scala and compile it using
scalac Contact.scala
, The scala compiler will create .class files for every class in that .sclaa file in appropriate package. In my case i have only one class in my Contact.scala so it creates Contact.class -
Next use javap Contact and and i can see following output being generated on the command line
Compiled from "Person.scala" public class Contact extends java.lang.Object{ private java.lang.String firstName; private java.lang.String lastName; public java.lang.String firstName(); public void firstName_$eq(java.lang.String); private java.lang.String lastName(); private void lastName_$eq(java.lang.String); public Contact(); }
Using AngularJs in Worklight/PhoneGap application
Angular.js is a JavaScript MVC framework, that makes development of HTML applications easy. I wanted to figure out how to use it for developing Worklight application so i followed these steps to build simple Hello AngularJs application
- First create a WorkLight application using WorkLight wizard, make sure that it works
- Next make changes in the index.html or entry page of your application to include angular.js from Google CDN and also add
<p>Hello {{'World'.length}}</p>
to test if AngularJs template is working
<!DOCTYPE HTML>
<html>
<head>
<meta charset="UTF-8">
<title>HelloWorld</title>
<meta name="viewport" content="width=device-width,
initial-scale=1.0, maximum-scale=1.0,
minimum-scale=1.0, user-scalable=0">
<link rel="shortcut icon" href="images/favicon.png">
<link rel="apple-touch-icon" href="images/apple-touch-icon.png">
<link rel="stylesheet" href="css/HelloWorld.css">
<script>window.$ = window.jQuery = WLJQ;</script>
</head>
<body id="content" style="display: none;" ng-app>
<h1>Hello Angularjs</h1>
<p>Hello {{'World'.length}}</p>
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.0.6/angular.min.js" />
<script src="js/initOptions.js"></script>
<script src="js/HelloWorld.js"></script>
<script src="js/messages.js"></script>
</body>
</html
After deployment you will notice that it prints Hello + length of 'world' which is 5 characters like this

Book review IBM Websphere Portal 8: Web Experience Factory and the Cloud
It seems that IBM is investing a lot in IBM Web Experience factory in last few years. I wanted to learn about WEF but the problem is i was not able to find any suitable documentation or something that will let me learn about WEF in step by step manner. Then before few days Packt publishing contacted me to review the IBM Websphere Portal 8: Web Experience Factory and the Cloud book. This book has lot of information about the architecture, analysis and design, release management in the first part. The part that i was most interested in was from chapter 7 to chapter 15 which covers the websphere experience factory development. I went through these chapters and really enjoyed reading them. I want to thank Packtpub for coming up with a book that helped me learn about WebSphere experience factory
Securing REST service created using WEF
In the Exposing REST + JSON endpoint using WEF i blogged about how to create a REST + JSON endpoint using WEF, but problem with that service is it is not protected. Anyone can call that service if you know the URL. So i wanted to protect the service and once the service is protected i can get the logged in user's information in the service.
I followed these steps to secure the service
Open the
After saving your changes deploy them on server
Once your application is deployed you will have to map the roles using WAS Admin Console before it actually get secured, so login into the WAS admin console and find the application that you want to secure and go to its Security Role to user/group mapping page and map
After saving your changes restart the application.
Now if you take the service URL and paste it in new browser window, it will redirect you to login page like this
Login on this page, In my case only user i have is
- First i changed the HelloWorldService.sayHello() method so that instead of asking user for name it reads the current logged in users name and returns it in
Hello name
formatpackage com.webspherenotes.wef; import com.bowstreet.webapp.WebAppAccess; public class HelloWorldService { public String sayHello(WebAppAccess webAppAccess){ System.out.println("Entering HelloWorldService.sayHello()"); String userId = webAppAccess.getUserInfo().getUserID(); System.out.println("Value of userId " + userId); return "Hello " + userId; } }
- If you look at the web.xml file of your WEF project you will notice that it has 3 servlets, out of that
WebEngineServlet
is the one that is used to expose REST service, In order to protect the REST service, you will want to protect the
WebEngineServlet
, if you look into web.xml file generated by web.xml it has 4 security constraints in it, you can use one of them to protect the WebEngineServlet. This is how the out of box SecurityConstraint_4
looks like
<security-constraint id="SecurityConstraint_4">
<web-resource-collection id="WebResourceCollection_4">
<web-resource-name>ProtectedSampleModels</web-resource-name>
<url-pattern>/webengine/factory/samples/protectedSamples/*</url-pattern>
</web-resource-collection>
<auth-constraint id="AuthConstraint_4">
<description>Roles allowed to execute sample protected models under
factory/samples/protectedSamples</description>
<role-name>IBMAdministrators</role-name>
<role-name>AllAuthenticatedUsers</role-name>
</auth-constraint>
</security-constraint>
I want to change it so that it protects /webengine/*
URL instead of only protectedSamples
, but if i make chanes in web.xml directly they will get overwritten during regeneration. Instead if you want to make any changes that would be included in generated web.xml you should make those changes in \WebContent\WEB-INF\bin\deployment\standalone.web.xml
file
\WebContent\WEB-INF\bin\deployment\standalone.web.xml
file, and change SecurityConstraint_4
look like this
<security-constraint id="SecurityConstraint_4">
<web-resource-collection id="WebResourceCollection_4">
<web-resource-name>ProtectedSampleModels</web-resource-name>
<url-pattern>/webengine/*</url-pattern>
</web-resource-collection>
<auth-constraint id="AuthConstraint_4">
<description>Roles allowed to execute sample protected models under
factory/samples/protectedSamples</description>
<role-name>IBMAdministrators</role-name>
<role-name>AllAuthenticatedUsers</role-name>
</auth-constraint>
</security-constraint>
AllAuthenticatedUser
to All Authenticated in Applications's Realm
group like this
wpsadmin
so use it to login and then you can get the service page like this
Exposing REST + JSON endpoint using WEF
I wanted to figure out how to create a REST + JSON end point using WEF. So i decided to create a simple Java class that has
sayHello(name)
method, this method takes name as input and when you invoke it it returns Hello name
as output
These are the steps that i followed
-
I did create a HelloWorldService.java class like this
package com.webspherenotes.wef; public class HelloWorldService { public String sayHello(String name){ System.out.println("Inside HelloWorldService.sayHello() Name = " + name); return "Hello " + name; } }
- Next i did create one empty model and i did name it HelloWorldServiceProvider.model
- THen in the HelloWorldServiceProvider.model i did add one Linked Java Object that points to HelloWorldService class like this
- Define HelloWorldService using Service Definition builder like this
- Now define
sayHello()
operation in the HelloWorldService using Service Operation builder like this - With this we have a Service Provider model, Now we need to consumer it and expose it as REST Service, For that create another empty model called HelloWorldRESTService.model
- Add Service Consumer builder in the HelloWorldServiceConsumer.model like this
- Add a REST Service Enable builder in this model and expose it as JSON like this
- Now your application is ready so publish it on server
Using portletHelper linked java object
The Web Experience factory tries to hide the portlet request phases from you. But some time you might be interested in knowing what phase your Linked Java object method is getting executed, If that's the case you should use
portletHelper
Linked Java Object.
So as soon as you add a Portlet Adapter builder to your model, the WPF will add portletHelper
Linked Java Object to that model like this
In your Linked Java Object you can call methods of portletHelper
LJO like this
public class PortletHelperDemoLJO {
public String sayHello(WebAppAccess webAppAccess){
System.out.println("Inside PortletHelperDemo.sayHello() ");
System.out.println("portletHelper.isPortletActionRequest -> " +webAppAccess.processAction("portletHelper.isPortletActionRequest"));
System.out.println("portletHelper.isPortletRenderRequest -> " +webAppAccess.processAction("portletHelper.isPortletRenderRequest"));
return "Hello from PortletHelperDemoLJO.sayHello() " + webAppAccess.getCurrentPage();
}
}
If you want you can call this from action list like this
Use Worklight to encrypt the data stored in window.localStorage
In the Reading data stored in localStroage by Android Device or Google Chrome Browser entry i talked about how easy it is to read data stored by web application in the window.localStorage object. WOrklight provides alternative which is to use a Encrypted cache that still uses
window.localStorage
object to store the data but encrypts the actual data to make it harder for someone else to read that data, even if they get access to your mobile or desktop. I wanted to try this feature out so i built this simple application which lets me store and read data from encrypted cache
First i did build a simple HTML file like this
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8" />
<meta name="viewport" content="width=device-width,
initial-scale=1.0, maximum-scale=1.0, minimum-scale=1.0, user-scalable=0" />
<title>HelloEncryptedCache</title>
<link rel="shortcut icon" href="images/favicon.png" />
<link rel="apple-touch-icon" href="images/apple-touch-icon.png" />
<link rel="stylesheet" href="css/reset.css" />
<link rel="stylesheet" href="css/HelloEncryptedCache.css" />
</head>
<body onload="WL.Client.init({})" id="content" style="display: none">
<h1>Encrypted Cache</h1>
<table>
<tr>
<td>Encryption Key</td>
<td><input type="text" name='encryptionKey' id="encryptionKey" /></td>
</tr>
<tr>
<td><button id="openCache">Open Cache</button></td>
<td><button id="closeCache">Close Cache</button></td>
</tr>
<tr>
<td><button id="destroyCache">Destroy Cache</button></td>
</tr>
<tr>
<td>Key</td>
<td><input type="text" name='key' id="key" /></td>
</tr>
<tr>
<td>value</td>
<td><input type="text" name='value' id="value" /></td>
</tr>
<tr>
<td><button id="encryptKey">Encrypt Key/Value</button></td>
<td><button id="decryptKey">Decrypt Key</button></td>
</tr>
<tr>
<td><button id="removeKey">Remove key</button></td>
</tr>
</table>
<script src="js/HelloEncryptedCache.js"></script>
<script src="js/messages.js"></script>
<script src="js/auth.js"></script>
</body>
</html>
This is how my JavaScript on the page looks like
window.$ = WLJQ;
function wlCommonInit(){
$("#openCache").click(function(){
console.log('The openCache button is clicked ' +$("#encryptionKey").val());
WL.EncryptedCache.open($("#encryptionKey").val(), true, function(){
console.log('The cache key opened successfully');
},onOpenError);
});
$("#closeCache").click(function(){
console.log('The closeCache button is clicked');
WL.EncryptedCache.close(function(){
console.log('The cache is closed successfully');
});
});
$("#destroyCache").click(function(){
console.log('The destroyCache button is clicked');
WL.EncryptedCache.destroy(function(){
console.log('Successfully destroyed the encrypted cache');
});
});
$("#encryptKey").click(function(){
console.log('The encryptKey button is clicked');
WL.EncryptedCache.write($("#key").val(), $("#value").val(), function() {
console.log('The entry written successfully');
}, function(status){
console.log('There was error in encryptingKey ' + status);
switch(status){
case WL.EncryptedCache.ERROR_KEY_CREATION_IN_PROGRESS:
console.log('Error in key creation process');
break;
case WL.EncryptedCache.ERROR_LOCAL_STORAGE_NOT_SUPPORTED:
console.log('Local storage is not supported');
break;
case WL.EncryptedCache.ERROR_NO_EOC:
console.log('No EOC');
break;
case WL.EncryptedCache.ERROR_COULD_NOT_GENERATE_KEY:
console.log('Could not generate key');
break;
case WL.EncryptedCache.ERROR_CREDENTIALS_MISMATCH:
console.log('Credentials mismatch');
break;
}
});
});
$("#decryptKey").click(function(){
console.log('The decryptKey button is clicked');
WL.EncryptedCache.read($('#key').val(), function(value) {
console.log('Value from the encrypted cache is ' + value);
alert('Encrypted value for the key -> ' + value);
}, function(status){
console.log('There was error in encryptingKey ' + status);
switch(status){
case WL.EncryptedCache.ERROR_KEY_CREATION_IN_PROGRESS:
console.log('Error in key creation process');
break;
case WL.EncryptedCache.ERROR_LOCAL_STORAGE_NOT_SUPPORTED:
console.log('Local storage is not supported');
break;
case WL.EncryptedCache.ERROR_NO_EOC:
console.log('No EOC');
break;
case WL.EncryptedCache.ERROR_COULD_NOT_GENERATE_KEY:
console.log('Could not generate key');
break;
case WL.EncryptedCache.ERROR_CREDENTIALS_MISMATCH:
console.log('Credentials mismatch');
break;
}
});
});
$("#removeKey").click(function(){
console.log('The removeKey button is clicked');
WL.EncryptedCache.remove($('#key').val(), function(){
console.log('The encrypted key removed successfully ->' + $('#key').val() );
})
});
}
function onOpenError(status) {
console.log("Inside onOpenError " + status);
switch (status) {
case WL.EncryptedCache.ERROR_KEY_CREATION_IN_PROGRESS:
console.log("Error key creation in progress");
break;
case WL.EncryptedCache.ERROR_LOCAL_STORAGE_NOT_SUPPORTED:
console.log("Error local storage not supported");
break;
case WL.EncryptedCache.ERROR_CREDENTIALS_MISMATCH:
console.log("Error credentials mismatch");
break;
case WL.EncryptedCache.ERROR_SECURE_RANDOM_GENERATOR_UNAVAILABLE:
console.log("Error secure random generator unavailable");
break;
case WL.EncryptedCache.ERROR_NO_EOC:
console.log("Error no eoc");
break;
}
}
The JavaScript has one event handler for each of the button and when you click on the button it makes use of the WL.EncryptedCache API to read/write cache entries. While working with encrypted cache first you have to open the cache before you can write any entry and once your done writing cache entries you will have to close the cache. I noticed one strange thing is if i dont attach error handling functions then my code works in normal browser but it throws undefined error in ANdroid emulator. It seems that the Worklight API makes use of some native device functionality to get encrypted cache working. One thing i noticed is accessing encrypted cache (specially opening it is really slow, so you should use it only if you really need to encrypt the data)
After storing data using the Encrypted Cache API i tried to access the file_0.localstorage
file from the device but i could not download it due to some file access level restrictions that android is putting on it.
Also in the local browser i can not read the values stored in the encryptedCache
Reading data stored in localStroage by Android Device or Google Chrome Browser
While working on my Using localStorage/sessionStorage in PhoneGap application example i was trying to debug a issue on the Android device where the data was not getting stored properly (Due to my programming mistake) and i wanted to figure out what data is actually getting stored so i used these steps.
- First i used the DDMS view in Eclipse to get access to the local file system on Andorid. All the data for an application is stored in andorid in
data/data/<apppackage>
folder, In my case application package name iscom.HelloLocalStorage
Whatever you store inwindow.localStorage
object is actually stored in thedata/data/<apppackage>/app_database/file_0.localstorage
file, first download it to your computer. This file is actually SQLLite database, so if you open it in normal notepad you wont be able to read it. When you store data inlocalStroage
object in the Google chrome it gets stored inC:\Users\<username>\AppData\Local\Google\Chrome\User Data\Default\Local Storage
directory. - If you want to open SQLLite database you will have to use one of the admin tools, i used the MikeTS SQLLite Management tool to open the file_0.localstorage file and it seems that Google Chrome stores the
localStorage
data inItemTable
, that table has 2 columns one is key and other is value, when i queried theItemTable
i could see the data stored in local preferences like this
Using localStorage/sessionStorage in PhoneGap application
The HTML 5 specification introduced 2 objects that can be used for storing data in key-value format on the client side, i wanted to try this feature out so i did create this simple Todo list web page that can be used to create a TO DO list.
This is how my Todo list application looks like
This is the HTML page that i created for working with
<!DOCTYPE html>
<html manifest="storage.appcache">
<head>
<title>Offline Application Example</title>
<script type="text/javascript" charset="utf-8"
src="jquery.js"></script>
<script type="text/javascript" charset="utf-8">
var storage = window.localStorage;
$(document).ready(function(){
console.log('Inside document.ready');
initTodoList();
$("#clearStorage").click(function(){
console.log('Entering clearstorage');
storage.clear();
$('li').remove();
console.log('Exiting clearstorage');
});
});
function remove_item(key){
console.log('Entering remove_item');
storage.removeItem(key);
console.log('Find and remove element with id = ' + key)
$('#'+key).remove();
console.log('Exiting remove_item');
}
function add_item() {
console.log('Entering add_item');
var d = new Date();
var key = d.getTime();
var value = $('#new_item').val();
storage.setItem(key,value);
createToDoListItem(key,value);
$("#new_item").val('');
console.log('Exiting add_item');
}
function initTodoList(){
console.log("Entering initTodoList " + storage.length);
for(var i = 0; i < storage.length; i++){
var key = storage.key(i);
var value = storage.getItem(key);
createToDoListItem(key,value);
}
}
function createToDoListItem(key, value){
var html = '<li data-key="'+key+'" id="'+key+'">'
+value+'<button onclick="javascript:remove_item(\''+ key+ '\')"
>Delete</button></li>';
console.log('Appending html ' + html)
$("#todo_list").append(html);
}
</script>
</head>
<body>
<input type="text" id="new_item">
<button onclick="add_item()">
Add
</button>
<ul id="todo_list">
</ul>
<br/>
<button id="clearStorage">Clear storage</button>
</body>
</html>
You can use either localStorage, in which case the data is storage across browser restarts or you can use the sessionStorage in which case you will loose the TODO list once the browser is closed. All you have to do is change the value of var storage =
either window.localStorage
or window.sessionStorage
Chrome developer tools allows us to look at the data stored in the localStorage as well as remove that data.
Subscribe to:
Posts (Atom)