Friday, December 11, 2015

What happens when Enable-SPSessionStateService -DefaultProvision


Powershell command
Enable-SPSessionStateService -DefaultProvision 
The changes to the SQL server and web site are as follows:
1) SQL server
In the sql server a new Database will be created as 
"SessionStateService_706b1a65e15248618a0090cd50ed1823"
2) Web.config changesIn the web.config file he below entry is inserted

<system.web>
...
<sessionState mode="SQLServer" timeout="60" allowCustomSqlDatabase="true" sqlConnectionString="Data Source=shaamils_SqlServer;Initial Catalog=SessionStateService_706b1a75e15248618a0090cd60ed4813;Integrated Security=True;Enlist=False;Pooling=True;Min Pool Size=0;Max Pool Size=100;Connect Timeout=15" />
</system.web>

<modules runAllManagedModulesForAllRequests="true">
...
<add name="Session" type="System.Web.SessionState.SessionStateModule" />
</modules>

IIS settings for Session State Managemnt

This might be useful when deciding on how to manage session state in a web application. Bu default session sate is set to "InProc" in IIS. In scenarios where you might have to persists the state in DB for instance Oracle DB you have to code your own session state provider. In such cases the IIS session state has to be changed to "Custom" as below.




Sunday, May 24, 2015

Open Modal dialog in SharePoint

You can use a JavaScript function for this purpose.

1) When you don't require a return from the Modal dialog.

    function openModalWindow(strPageURL) {
        var options = {
            url: strPageURL,
            title: "Title goes here",
            showClose: true,
            width: 600,
            height: 400,
            allowMaximize: false
        };

        SP.SOD.execute('sp.ui.dialog.js', 'SP.UI.ModalDialog.showModalDialog', options);
    }

2) When a return value is required to be captured by the Parent page

Include a callback parameter in the options specified

Option 1: Include in the options parameter collection

function openModalWindow(strPageURL) {
        var options = {
            url: strPageURL,
            title: "Title goes here",
            showClose: true,
            width: 600,
            height: 400,
            allowMaximize: false
            dialogReturnValueCallback: CloseDialogCallback
        };

        SP.SOD.execute('sp.ui.dialog.js', 'SP.UI.ModalDialog.showModalDialog', options);
    }

Option 2: Place the code after other option parameters are defined

var options = {
                url: strPageURL,
                allowMaximize: false
                showClose: true
            };
            options.dialogReturnValueCallback = Function.createDelegate(null, CloseDialogCallback);

            SP.SOD.execute('sp.ui.dialog.js', 'SP.UI.ModalDialog.showModalDialog', options);


In the invoked function, you could specify the actions to do once the Modal Dialog closes, such as refreshing the parent page

function CloseDialogCallback(dialogResult, returnValue) {
            if (returnValue.d) {
               /*Do something */
            }
            if (dialogResult == SP.UI.DialogResult.OK) {
                SP.SOD.execute('sp.ui.dialog.js', 'SP.UI.ModalDialog.RefreshPage', SP.UI.DialogResult.OK);
            }
        }

3) Closing the Modal Dialog (Add script to the page in the Modal Dialog)

This can be done in two ways

  • Without referencing the SP.UI.Dialog.js
function closeOnCancel() {
            window.frameElement.commonModalDialogClose(0 /* 0 for cancel */, 'Cancelled');
        }

function closeOnOk() {
            window.frameElement.commonModalDialogClose(1 /* 1 for ok */, 'OK result');
        }

- OR - 

  • using the SP.UI.Dialog.js

Reference the JavaScript on your page.
<script src="/_layouts/15/SP.UI.Dialog.js" type="text/javascript"></script>

function closeOnCancel() {
            SP.UI.ModalDialog.commonModalDialogClose(SP.UI.DialogResult.Cancel, 'Cancelled');
        }
function closeOnOk() {
            SP.UI.ModalDialog.commonModalDialogClose(SP.UI.DialogResult.OK, 'OK result');
        }

To call these JavaScript functions from server side code use ScriptManager:

ScriptManager.RegisterStartupScript(this, this.GetType(), "closeScript", "closeOnOk();", true);

However, the final JavaScript function might give out a JavaScript error in some Internet Explorer versions.



Saturday, May 23, 2015

JavaScript Takeaways for .Net Developers

1) Capture server controls where ClientIDMode is not set to Static

document.getElementById("<%= txtRule.ClientID %>").value

2) Storing Session value in JavaScript variable

var userAttempts = '<%= Session["userAttemptSession"] %>';


3) Manipulating Hidden field values

/*Get value*/
var hitCountContainer = document.getElementById("hdnMyCount")
var hitCount = parseInt(hitCountContainer.value);
hitCount = hitCount + 1;

/*Set Value*/
hitCountContainer.value = hitCount.toString()

4) Invoking a post-back (without any parameteres)

__doPostBack('', '');

5) Invoking post-back (including parameter passing)

__doPostBack('hdnMyCount', hitCount.toString());

Accessing the post-back parameters in Page_Init

string controlName = Request.Params["__EVENTTARGET"];
string controlValue = Request.Params["__EVENTARGUMENT"];

This example may be useful in a scenario where you need the client-side updated values during the Page_Init. Reason is that the values are not accessible at this point of the ASP.Net Page Life Cycle. If you need to access hidden fields during Page_Load this is not necessary as the values are already accessible by that time (of the ASP.Net Page Life Cycle). Dynamically generating Controls in an application page on user request (eg: add new row having ASP.Net controls) would be an ideal scenario.

FYI:
There is a nice little image of the ASP.Net Page Life Cycle in this MSDN Blog. Adorable isn't it ?   ;) The very essence of ASP.Net forms programming !!
         
6) Sending multiple parameters in JavaScript postback

Here I send two JavaScript variables count & type.

__doPostBack('addNew', JSON.stringify({ count: count.toString(), type: selectedText}));

In the server side capture using the following

/*Using directive*/
using System.Web.Script.Serialization
...
...
/*Code logic*/
string receivedArgs = Request.Params["__EVENTARGUMENT"];
var arguments = new JavaScriptSerializer().Deserialize<Dictionary<string, object>>(receivedArgs);
var countValue = arguments["count"];
var typeValue = arguments["type"];


Sunday, February 22, 2015

CAML Query - 3 AND 's in 1

It's pretty easy to deal with two conditions in CAML query. A newbie would find it to be a bit tricky when it comes to more than two. CAML has it's own way of grouping conditions. Below is a sample showing how to do it.

<Where>
<And>
<And>
<Eq>
          <FieldRef Name='_ModerationStatus'/>
          <Value Type='String'>Approved</Value>
</Eq>
<Neq>
<FieldRef Name='ContentType' />
<Value Type='Text'>Folder</Value>
</Neq>
</And>
<Neq>
<FieldRef Name='******' />
<Value Type='Text'>*****</Value>
</Neq>
</And>
</Where>




Saturday, February 21, 2015

Playing around with the TreeView

Playing around with the ASP.Net TreeView.

Initially a TreeNode is created and child nodes are added under the node.

        TreeNode tree = new TreeNode();
        
        tree.Value = "Social Media";
        tree.ImageUrl = "/images/home.png";
        tree.ChildNodes.Add(new TreeNode("Facebook", "Facebook","/images/fb.png"));
        tree.ChildNodes.Add(new TreeNode("G+","GPlus","/images/google.png"));
        tree.ChildNodes.Add(new TreeNode("Printrest", "Printrest", "/images/pintrest.png"));
        tree.ChildNodes.Add(new TreeNode("Twitter", "Twitter", "/images/twitter.jpg"));

Now lets add some child nodes under the created nodes. In this example the below would be the leaf nodes.

            foreach (TreeNode node in tree.ChildNodes)
            {
                node.ChildNodes.Add(new TreeNode("Sri Lanka", string.Concat(node.Value,"-","SL"), "/images/countries/SL-flag.jpg"));
                node.ChildNodes.Add(new TreeNode("Malaysia", string.Concat(node.Value,"-","ML"), "/images/countries/malaysia-flag.png"));
                node.ChildNodes.Add(new TreeNode("USA", string.Concat(node.Value,"-","USA"), "/images/countries/US-Flag.png"));
                node.ChildNodes.Add(new TreeNode("Britain", string.Concat(node.Value,"-","BRIT"), "/images/countries/Britain-flag.png"));
                node.ChildNodes.Add(new TreeNode("Australia", string.Concat(node.Value,"-","AUS"), "/images/countries/Australia-Flag.png"));
                node.ChildNodes.Add(new TreeNode("Netherlands", string.Concat(node.Value,"-","NL"), "/images/countries/netherlands-flag.png"));
                node.ChildNodes.Add(new TreeNode("Egypt", string.Concat(node.Value,"-","EG"), "/images/countries/Egypt-Flag.png"));
                node.ChildNodes.Add(new TreeNode("Greece", string.Concat(node.Value,"-","GR"), "/images/countries/greece_flag.png"));
                node.ChildNodes.Add(new TreeNode("Germany", string.Concat(node.Value,"-","GE"), "/images/countries/germany-flag.png"));
                node.ChildNodes.Add(new TreeNode("Canada", string.Concat(node.Value,"-","CA"), "/images/countries/canada_flag.png"));
                node.ChildNodes.Add(new TreeNode("Brazil", string.Concat(node.Value,"-","BR"), "/images/countries/brazil-flag.png"));
            }

 The TreeNode is then set to a TreeView to be displayed in the Form.

        TreeView view = new TreeView();
        view.ShowCheckBoxes = TreeNodeTypes.All;
        view.Nodes.Add(tree);
        view.TreeNodeCheckChanged += view_TreeNodeCheckChanged;
        view.Attributes.Add("onclick", "postBackByObject()");

        form1.Controls.Add(view);

Here, notice the JavaScript method postBackByObject() which does the job of auto postbacking on clicking on a Checkbox of a Node. For this purpose you need to add the following script in the ASPX page. Auto post backing comes in handy when you need to check or uncheck the set of child-nodes belonging to a selected node.


    <script type="text/javascript">
        function postBackByObject() {
            var o = window.event.srcElement;
            if (o.tagName == "INPUT" && o.type == "checkbox") {
                __doPostBack("", "");
            }
        }
    </script>

To programmatically check or uncheck child nodes of a node, use the TreeNodeCheckChanged event. A sample code would be:

    void view_TreeNodeCheckChanged(object sender, TreeNodeEventArgs e)
    {
        if (e.Node.Checked)
        {
            CheckChildNodes(e.Node.ChildNodes);
        }
        else if (e.Node.Checked == false)
        {
            UncheckChildNodes(e.Node.ChildNodes);
        }
    }

    private void UncheckChildNodes(TreeNodeCollection children)
    {
        foreach (TreeNode child in children)
        {
            if (child.Checked)
                child.Checked = false;
            UncheckChildNodes(child.ChildNodes);
        }
    }

    private void CheckChildNodes(TreeNodeCollection children)
    {
        foreach (TreeNode child in children)
        {
            if (child.Checked == false)
                child.Checked = true;
            CheckChildNodes(child.ChildNodes);
        }
    }

Then you get the resulting tree as below. The data in this view is created merely for illustration purposes of the ASP.Net TreeView and has no actual meaning.




Friday, February 20, 2015

AJAX call from Visual Web Part - SharePoint

1)
In the JavaScript function create the JSON object. Here the stringify method is used to construct the object which contains the parameters to be sent. The function in the JavaScript method of the aspx page is as below:


    function CallMyPage(itemValue, paramTwo, paramThree, paramFour) {

        var final = { myItem: itemValue, parameterTwo: paramTwo, parameterThree: paramThree, siteUrl: paramFour };

        $.ajax({
            type: "POST",
            url: paramFour + "/_layouts/15/MyFeatureFolder/WebMethods.aspx/MyWebMethod",
            data: JSON.stringify(final),
            contentType: "application/json; charset=utf-8",
            dataType: "json",
            success: OnSuccess,
           failure: function (response) {
             alert(response.d);
          }
       });
    }

2)
In the code behind within a SPGridView I have a HyperLink control. I set the JavaScript method call in the code behind as:

editLink.NavigateUrl = "javascript:CallMyPage('" + itemGuid.Text + "','" + MyParamTwo + "' ,'" + MyParamThree + "', '" + SPContext.Current.Web.Url + "');"


3)
In my approach instead of a web service I am using an application page (WebMethods.aspx) to get the job done. In the application page servicing the AJAX call, I create the web method

        [System.Web.Services.WebMethod]
        public static string MyWebMethod(string myItem, string parameterTwo, string parameterThree, string siteUrl)
        {
            string result = string.Empty;
            try 
            {
                //TODO - Process request and return result
            }
            catch (Exception)
            {
                //Exception Handling
            }
            return result;

4)
On success

    function OnSuccess(response) {

        if (response.d) {           
            /* Handle  result */            
        }
    }

Note: I have used the jquery-1.11.2.min.js file in my solution

Saturday, January 17, 2015

Adding Custom Properties to a Visual Web Part

When the Visual web part is generated in Visual Studio (Eg; VS 2013). It contains mainly 3 components. The web part file, user control a ASCX file and the code behind for the user control

The web part is generated with the following code in the CreateChildControls() method

private const string _ascxPath = @"~/_CONTROLTEMPLATES/15/....../MyWebPartUserControl.ascx";

protected override void CreateChildControls()
{
  Control control = Page.LoadControl(_ascxPath);
  Controls.Add(control);
}

Here, the .ascx could not access the custom web part properties.
When adding custom properties to the Visual web part,  few changes are required.

1) Create a property in the user control, of the web part class type.

public MyVisualWebPart ParentWebPart { get; set; }

2) Set the web part to the user controls parent property

Inside the web part file's CreateChildControls() method change the code to:

MyVisualWebPartUserControl control = (MyVisualWebPartUserControl)Page.LoadControl(_ascxPath);
//Set the web part to the users controls parent property                                                                             
control.ParentWebPart = this;
Controls.Add(control);    

Now the custom web part properties are accessible from the user control !                                                                                                              

3) Add the required custom properties into the web part file

        private string customPropertyOne;                           
        [Category("My WebParts Custom Settings"),           
        Personalizable(PersonalizationScope.Shared),          
        WebBrowsable(true),                                              
        WebDisplayName("Custom Property One"),            
        WebDescription("This is my first custom property")] 
        public string CustomPropertyOne                             
        {                                                                             
            get { return customPropertyOne; }                      
            set { customPropertyOne = value; }                    

        }                                                                            

4) Access the property in the ASCX file

Now you can access the custom property via:

ParentWebPart.CustomPropertyOne


Saturday, January 10, 2015

Edit Windows Registry


To open up the registry editor, Type "regedit" in "run".

To create a folder,  right click on a node(folder) and select "New > Key"

To create a registry key, right click on the folder you need to create the registry key. Select  "New > String Value"


Sunday, January 4, 2015

Allow CAML Query to get items inside Library Folders

Usually a CAML query would query a SharePoint library and get all available items matching the where clause, except the ones within folders of the Library. There is a property which needs to be explicitly set, in order for the query to return all items pertaining to the where clause, including the ones inside folders and nested folders. In the view attribute, the scope needs to be set to Recursive All. A sample CAML query would be:


SPListItemCollection itemCollection = null;
...
...
SPQuery myQuery = new SPQuery();

myQuery.ViewFields = @"<FieldRef Name='UniqueId'/>
                                            <FieldRef Name='ContentType'/>
                                            <FieldRef Name='ID'/><FieldRef Name='FileLeafRef'/>";

                string whereClause = @"<Where>
                                    <Eq>
                                        <FieldRef Name='" + myVariableOne + @"' />
                                            <Value Type='Text'>" + myVariableTwo + @"</Value>
                                    </Eq>
                                  </Where>";

myQuery.Query = whereClause;
myQuery.ViewAttributes += " Scope='RecursiveAll'";


Now use the SPLists GetItems() method to execute the query
Eg: testLibrary.GetItems(myQuery);




Services available in SharePoint Foundation 2013

SharePoint Foundation only has a few services available when compared to the Server version.
Namely they are:


  • App Management Service
  • Business Data Connectivity Service
  • Lotus Notes Connector
  • Search Service Application
  • Secure Store Service
  • State Service
  • Usage and Health data collection

Saturday, January 3, 2015

Add a new Row to DataTable in DataSet and Push the update to Database


Example is as below:

            string connectionString = "Data Source=****;Initial Catalog=master;Persist Security Info=True;User ID=**;Password=****";

            using (SqlConnection conn = new SqlConnection(connectionString))
            {
                using (SqlCommand command = new SqlCommand("select top 10 * from Test", conn))
                {

                    conn.Open();
                    SqlDataAdapter adapter = new SqlDataAdapter(command);
                    DataSet ds = new DataSet();
                    adapter.Fill(ds);

                    DataRow row = ds.Tables[0].NewRow();
                    row["EID"] = "006";
                    row["Name"] = "Saman";
                    row["Tel"] = "01115342";
                    row["Residence"] = "Galle, Sri Lanka";

                    ds.Tables[0].Rows.Add(row);

                    //Update Database
                    SqlCommandBuilder cb = new SqlCommandBuilder(adapter);
                    cb.DataAdapter.Update(ds.Tables[0]);
                }
            }