Monday, August 4, 2014

Testing rest api's using Rest-Assured

1. Add the following dependencies in your pom.xml
<dependency>
      <groupId>com.jayway.restassured</groupId>
      <artifactId>rest-assured</artifactId>
      <version>2.3.1</version>
      <scope>test</scope>
</dependency>
<dependency>
      <groupId>com.jayway.restassured</groupId>
      <artifactId>json-path</artifactId>
      <version>2.3.1</version>
</dependency>
<dependency>
      <groupId>com.jayway.restassured</groupId>
      <artifactId>json-schema-validator</artifactId>
      <version>2.3.1</version>
      <scope>test</scope>
</dependency>
2. Set the baseURI in @BeforeMethod
RestAssured.baseURI = "http://yoururl.com"; 
RestAssured.port = 80;
3.  In @Test add the following code to get the response from the api
Response response = get("/api/xxx/xxxx");   
          JsonPath jsonpath = new JsonPath(response.asString());
          String ca_id = jsonpath.getString("id");          // id will get all the values from json response and returns a json string. You could validate whatever you are looking for here.

Happy Testing!!!!

Sunday, August 3, 2014

Chrome driver initialization in Webdriver

Follow to below steps to work with Chrome 

1. Download the chrome driver 2.41.0
        Those who use maven, you could copy paste this dependency in your pom.xml
<dependency><groupId>org.seleniumhq.selenium</groupId><artifactId>selenium-chrome-driver</artifactId><version>2.41.0</version></dependency>
2.    If you work in mac machine, download chromedriver unix executable. If you work in windows machine, download chromedriver.exe
You could get it here
3. Save the chromedriver in your project path.

4. Refer the below code and initialize your chrome driver.
    String path_to_chromedriver_executable = System.getProperty("user.dir")+"/src/test/resources/chromedriver";  //mention the location where you kept your chromedriver unix executable or chromedriver.exe
         
System.setProperty("webdriver.chrome.driver", path_to_chromedriver_executable);
            ChromeOptions options = new ChromeOptions();
            options.addArguments ("--test-type" );
        driver = new ChromeDriver(options);

5. You are ready to launch chrome browser. Happy Testing!!!!!

Wednesday, July 30, 2014

ScrollDown utility - Selenium Webdriver

Scroll Down Utility

Step 1: 
Create a method scrollDown

public void scrollDown(int iter) throws InterruptedException{
JavascriptExecutor jse = (JavascriptExecutor)driver;
for(int i = 1;i<=iter;i++){
Thread.sleep(1000);
jse.executeScript("window.scrollBy(0,3000)", "");
Thread.sleep(1000);
}

}

Step 2: 
Call the method when ever you want to scroll.
scrollDown(1);



Archive Test Results after every run

Save the below script as archive_utility.vbs and add this in startup
'archive utility - Created on 24 -August-2012 by k.s.karthikeyan@gmail.com
Dim objFSO
strFilename = "emailable-report"
strExtn = ".html"
strFilename2 = "testng-failed"
strExtn2 = ".xml"
strSourceFolder = "c:\ebox\Karthik\2\MyProject\test-output"
'strSourceFolder1 = Replace(strSourceFolder,"\","\\\\")
'Wscript.echo strSourceFolder1
strDestFolder = "c:\Documents and Settings\ksankarappan\Desktop\archive\"
strComputer = "."
Set objWMIService = GetObject("winmgmts:" _
    & "{impersonationLevel=impersonate}!\\" & _
        strComputer & "\root\cimv2")
Set colMonitoredEvents = objWMIService.ExecNotificationQuery _
    ("Select * From __InstanceCreationEvent Within 5 Where " _
    & "Targetinstance Isa 'CIM_DirectoryContainsFile' and " _
    & "TargetInstance.GroupComponent= " _
    & "'Win32_Directory.Name=""c:\\\\ebox\\\\Karthik\\\\2\\\\MyProject\\\\test-output""'")
Do
    Set objLatestEvent = colMonitoredEvents.NextEvent
    temp = objLatestEvent.TargetInstance.PartComponent
   temp = Replace(Mid(temp, InStr(temp, Chr(34)) + 1), "\\", "\")
    temp = Left(temp, Len(temp) - 1)
Wscript.Echo temp
Wscript.Echo strSourceFolder & "\" & strFilename2 & strExtn
    if temp = strSourceFolder & "\" & strFilename & strExtn Then
Set objFSO = CreateObject("Scripting.FileSystemObject")
Today = "_" + Replace(Date, "/", "_") + "_" + Replace(FormatDateTime(Time, 3), ":","_")
 
objFSO.MoveFile strSourceFolder & "\" & strFilename & strExtn, strDestFolder & strFilename & Today & strExtn
'Wscript.echo "Emailable-Report.html is moved to the path : " & strDestFolder
    End If
    if temp = strSourceFolder & "\" & strFilename2 & strExtn2 Then
Set objFSO2 = CreateObject("Scripting.FileSystemObject")
Today = "_" + Replace(Date, "/", "_") + "_" + Replace(FormatDateTime(Time, 3), ":","_")
 
objFSO2.MoveFile strSourceFolder & "\" & strFilename2 & strExtn2, strDestFolder & strFilename2 & Today & strExtn2
'Wscript.echo "testng-failed.xml is moved to the path : " & strDestFolder
    End If
Loop

Tuesday, July 29, 2014

Alternative of Selenium Webdriver's drag and drop

At times, I felt Webdriver's drag and drop doesn't make us happy. I found an alternative which helps to perform drag and drop without any hustle. Just follow these 3 steps to make your test case working :)


Step 1: Save this below code in your build location and name it as "drag_and_drop_helper2.js"

(function( $ ) {

    var rkeyEvent = /^key/,
        rmouseEvent = /^(?:mouse|contextmenu)|click*/,
        rdndEvent = /^drag*|drop*/;

    $.fn.simulate = function( type, options ) {
        return this.each(function() {
            new $.simulate( this, type, options );
        });
    };

    $.simulate = function( elem, type, options ) {
        var method = $.camelCase( "simulate-" + type );

        this.target = elem;
        this.options = options;

        if ( this[ method ] ) {
            this[ method ]();
        } else {
            this.simulateEvent( elem, type, options );
        }
    };

    $.extend( $.simulate.prototype, {
        simulateEvent: function( elem, type, options ) {
            var event = this.createEvent( type, options );
            this.dispatchEvent( elem, type, event, options );

            if(type == "dragstart"){
                console.log("dragstart dropTarget: " + options.dropTarget
                )
            }

            if(type == "dragstart" && options.dropTarget){
                this._performDND(event, options);
            }
            var message = "simulated event " + type + " on " + elem.id;
            console.log(message);
        },

        _performDND: function(event, options){
            console.log("performing dnd, dropping on " + options.dropTarget.id)
            var dropEvent = this.createEvent("drop", {});
            dropEvent.dataTransfer = event.dataTransfer;
            this.dispatchEvent($(options.dropTarget)[0], "drop", dropEvent, {});
        },

        createEvent: function( type, options ) {
            if ( rkeyEvent.test( type ) ) {
                return this.keyEvent( type, options );
            }
            if(rmouseEvent.test(type)){
                return this.mouseEvent( type, options );
            }
            if(rdndEvent.test(type)){
                return this.dndEvent( type, options );
            }
        },

        dndEvent: function(type, options, dataTransfer){
            var event = document.createEvent("CustomEvent");
            event.initCustomEvent(type, true, true, null);
            event.dataTransfer = {
                data: {
                },
                setData: function(type, val){
                    this.data[type] = val;
                },
                getData: function(type){
                    return this.data[type];
                }
            };
            return event;
        },

        mouseEvent: function( type, options ) {
            var event, eventDoc, doc, body;
            options = $.extend({
                bubbles: true,
                cancelable: (type !== "mousemove"),
                view: window,
                detail: 0,
                screenX: 0,
                screenY: 0,
                // TODO: default clientX/Y to a position within the target element
                clientX: 1,
                clientY: 1,
                ctrlKey: false,
                altKey: false,
                shiftKey: false,
                metaKey: false,
                button: 0,
                relatedTarget: undefined
            }, options );

            if ( document.createEvent ) {
                event = document.createEvent( "MouseEvents" );
                event.initMouseEvent( type, options.bubbles, options.cancelable,
                    options.view, options.detail,
                    options.screenX, options.screenY, options.clientX, options.clientY,
                    options.ctrlKey, options.altKey, options.shiftKey, options.metaKey,
                    options.button, options.relatedTarget || document.body.parentNode );
                // IE 9+ creates events with pageX and pageY set to 0.
                // Trying to modify the properties throws an error,
                // so we define getters to return the correct values.
                if ( event.pageX === 0 && event.pageY === 0 && Object.defineProperty ) {
                    eventDoc = event.relatedTarget.ownerDocument || document;
                    doc = eventDoc.documentElement;
                    body = eventDoc.body;

                    Object.defineProperty( event, "pageX", {
                        get: function() {
                            return options.clientX +
                                ( doc && doc.scrollLeft || body && body.scrollLeft || 0 ) -
                                ( doc && doc.clientLeft || body && body.clientLeft || 0 );
                        }
                    });
                    Object.defineProperty( event, "pageY", {
                        get: function() {
                            return options.clientY +
                                ( doc && doc.scrollTop || body && body.scrollTop || 0 ) -
                                ( doc && doc.clientTop || body && body.clientTop || 0 );
                        }
                    });
                }
            } else if ( document.createEventObject ) {
                event = document.createEventObject();
                $.extend( event, options );
                // TODO: what is this mapping for?
                event.button = { 0:1, 1:4, 2:2 }[ event.button ] || event.button;
            }

            return event;
        },

        keyEvent: function( type, options ) {
            var event;
            options = $.extend({
                bubbles: true,
                cancelable: true,
                view: window,
                ctrlKey: false,
                altKey: false,
                shiftKey: false,
                metaKey: false,
                keyCode: 0,
                charCode: undefined
            }, options );

            if ( document.createEvent ) {
                try {
                    event = document.createEvent( "KeyEvents" );
                    event.initKeyEvent( type, options.bubbles, options.cancelable, options.view,
                        options.ctrlKey, options.altKey, options.shiftKey, options.metaKey,
                        options.keyCode, options.charCode );
                    // TODO: what is this supporting?
                } catch( err ) {
                    event = document.createEvent( "Events" );
                    event.initEvent( type, options.bubbles, options.cancelable );
                    $.extend( event, {
                        view: options.view,
                        ctrlKey: options.ctrlKey,
                        altKey: options.altKey,
                        shiftKey: options.shiftKey,
                        metaKey: options.metaKey,
                        keyCode: options.keyCode,
                        charCode: options.charCode
                    });
                }
            } else if ( document.createEventObject ) {
                event = document.createEventObject();
                $.extend( event, options );
            }

            // TODO: can we hook into core's logic?
            if ( $.browser.msie || $.browser.opera ) {
                // TODO: is charCode ever <0 ? Can we just use charCode || keyCode?
                event.keyCode = (options.charCode > 0) ? options.charCode : options.keyCode;
                event.charCode = undefined;
            }

            return event;
        },

        // TODO: does this need type? Can't we just check event.type?
        dispatchEvent: function( elem, type, event ) {
            if ( elem.dispatchEvent ) {
                elem.dispatchEvent( event );
            } else if ( elem.fireEvent ) {
                elem.fireEvent( "on" + type, event );
            }
        },

        simulateFocus: function() {
            var focusinEvent,
                triggered = false,
                element = $( this.target );

            function trigger() {
                triggered = true;
            }

            element.bind( "focus", trigger );
            element[ 0 ].focus();

            if ( !triggered ) {
                focusinEvent = $.Event( "focusin" );
                focusinEvent.preventDefault();
                element.trigger( focusinEvent );
                element.triggerHandler( "focus" );
            }
            element.unbind( "focus", trigger );
        },

        simulateBlur: function() {
            var focusoutEvent,
                triggered = false,
                element = $( this.target );

            function trigger() {
                triggered = true;
            }

            element.bind( "blur", trigger );
            element[ 0 ].blur();

            // blur events are async in IE
            setTimeout(function() {
                // IE won't let the blur occur if the window is inactive
                if ( element[ 0 ].ownerDocument.activeElement === element[ 0 ] ) {
                    element[ 0 ].ownerDocument.body.focus();
                }

                // Firefox won't trigger events if the window is inactive
                // IE doesn't trigger events if we had to manually focus the body
                if ( !triggered ) {
                    focusoutEvent = $.Event( "focusout" );
                    focusoutEvent.preventDefault();
                    element.trigger( focusoutEvent );
                    element.triggerHandler( "blur" );
                }
                element.unbind( "blur", trigger );
            }, 1 );
        }
    });



    /** complex events **/

    function findCenter( elem ) {
        var offset,
            document = $( elem.ownerDocument );
        elem = $( elem );
        offset = elem.offset();

        return {
            x: offset.left + elem.outerWidth() / 2 - document.scrollLeft(),
            y: offset.top + elem.outerHeight() / 2 - document.scrollTop()
        };
    }

    $.extend( $.simulate.prototype, {
        simulateDrag: function() {
            var target = this.target,
                options = this.options,
                center = findCenter( target ),
                x = Math.floor( center.x ),
                y = Math.floor( center.y ),
                dx = options.dx || 0,
                dy = options.dy || 0,
                target = this.target,
                coord = { clientX: x, clientY: y , dropTarget: options.dropTarget || undefined };

            console.log("simulateDrag of " + target.id +
                " from {" + coord.clientX + ", " + coord.clientY + "} " +
                "by {" + dx + ", " + dy + "}" );

            this.simulateEvent( target, "dragstart", coord );
            coord = { clientX: x + 1, clientY: y + 1 };
            this.simulateEvent( document, "mousemove", coord );
            coord = { clientX: x + dx, clientY: y + dy };
            this.simulateEvent( document, "mousemove", coord );
            this.simulateEvent( document, "mousemove", coord );
            this.simulateEvent( target, "mouseup", coord );
            this.simulateEvent( target, "dragend", coord );
        }
    });

})( jQuery );



Step 2: Add this method drag_and_drop_js . Change the path you just saved the helper file

private void drag_and_drop_js(WebElement source ,WebElement target){
         
         try {
                   
            String js_filepath =               System.getProperty("user.dir")+"/src/test/resources/drag_and_drop_helper2.js";   // Change the path here               
                   
                   String java_script="";
                   String text;

                   BufferedReader input = new BufferedReader(new FileReader(js_filepath));
                   StringBuffer buffer = new StringBuffer();

                   while ((text = input.readLine()) != null)
                       buffer.append(text + "\n");
                       java_script = buffer.toString();

                   input.close();

                         String load_jquery = "var jqueryUrl = \"http://code.jquery.com/jquery-2.1.1.min.js\";\n"
                                        + "var scriptElt = document.createElement('script');\n"
                                        + "scriptElt.type = 'text/javascript';\n"
                                        + "scriptElt.src = jqueryUrl;\n"
                                        + "scriptElt.src = jqueryUrl;\n"
                                        + "document.getElementsByTagName('head')[0].appendChild(scriptElt);";

   
                   JavascriptExecutor js = (JavascriptExecutor) driver;
                   driver.manage().timeouts().setScriptTimeout(10, TimeUnit.SECONDS);
                   
                   String drag_drop_script = "jQuery(arguments[0]).simulate('drag', { dropTarget: arguments[1] });";
                   Object o1 = js.executeScript(load_jquery);
                   Object o2 = js.executeScript(java_script);
                   Object o3 = js.executeScript(drag_drop_script,source,target);
                                 
         } catch (Exception e) {
             
                 System.out.println("Error :" + e.toString());
           }
         
        } 

Step 3: Get the source and destination elements, and your are done.

WebElement from = driver.findElement(By.xxxx("xxxx"));
WebElement to = driver.findElement(By.xxxx("xxxx"));
from.click();

drag_and_drop_js(from,to);


Happy Testing!!!