Advertisements

Bootstrap – Table style classes

January 14, 2019 Leave a comment

If you are new to Bootstrap, refer my previous article to get started with Bootstrap

In this article, lets see how to apply styles to table control.

Lets add a table, with 4 rows with no custom styling and it would render as below.

bs_tbl4

HTML table with no custom styling

Now lets see, how quickly we can apply Bootstrap styling and make the table responsive and vibrant.

bs_tbl2

Table with Responsive UI

In the above screen, browser has shrunk to fit to tablet dimensions but still the table has’t distorted which makes it responsive.

Below is the table script to achieve above styling

<div class=”container”>
<div class=”table-responsive”>
<table class=”table table-striped table-bordered table-hover“>

🙂

Advertisements
Categories: Bootstrap Tags: ,

Bootstrap – Popover

January 14, 2019 Leave a comment

If you are new to Bootstrap, refer my previous article to get started with Bootstrap

In this article, lets see how to get Popover notifications in <table> control.

Bootstrap, displays popover notifications using “popper.min.js” file, which comes with Bootstrap ‘Starter Template’.

To create a popover (Popup) message, add the data-toggle=”popover” attribute to the HTML element.

  • ‘title’ attribute to specify the header text of the popover
  • ‘data-content’ attribute to specify the text that should be displayed inside the popover’s body

Sample HTML:

Below is my <td> tag of my ‘Name’ column of the table row with data-toggle=”popover”

<td>
<a href=”#” data-toggle=”popover” title=”About” data-content=”Rajeev Pentyala is from India”>Rajeev Pentyala</a>
</td>

In the tag, add below content:

$(document).ready(function () {
$(‘[data-toggle=”popover”]’).popover();
});

Add data-toggle=”popover” to all your ‘Name’ columns and the output will come as below:

bs_pop1

🙂

Bootstrap – Getting started

January 14, 2019 2 comments

In this series, I am going to touch base Bootstrap fundamentals and controls. Lets see how to get started with Bootstrap.

What is Bootstrap?

  • Bootstrap is is the most popular CSS (Cascading Style Sheet) Framework for developing responsive and mobile-first websites.
  • Bootstrap framework provides helper css and js files, with which can make your website/web application vibrant and responsive with no additional effort.
bs_intro

Bootstrap – Responsive UI

What is ‘Responsive’ UI:

  • Responsive Web Design is about using HTML and CSS to automatically resize, hide, shrink, or enlarge, a website, to make it look good on all devices (desktops, tablets, and phones).
  • With Bootstrap framework you can make you web pages responsive and fit for all devices.

Below are the steps to use Bootstrap in a sample HTML page

Download the Bootstrap framework:

  • Download the Bootstrap components (i.e., CSS and JS files) from here
    • Note: Instead of downloading the files locally, you can also refer CDN files. Refer this link
bs_1

Download components locally

  • In this article I am downloading the components locally and use it in HTML file.
  • Once you download and unzip, you would notice 2 folders css and js

bs_2

Get start with a sample HTML page:

Once you download the Bootstrap components below are the steps to use Bootstrap in HTML file.

I am using Visual Studio as my code editor, you can also use the editors you are comfortable with.

  • Create a new “Asp.Net Empty Website”
  • Create a new folder “Bootstrap” and place the css and js folders of Bootstrap downloaded in prior section.

bs_3

  • Copy the HTML content from Starter Template of Bootstrap and paste it in your HTML file.
bs_4

Bootstrap – Start Template

  • You would notice the Bootstrap css and js files CDN’s references.
    • Note: CDN references will not work if your machine not connected to Internet.
  • Replace CDN references with local file references, since we already downloaded the Bootstrap files locally and added to Visual Studio.
bs_5

Replace CDN with local references

  • With out making any further changes, run the HTML page and you would notice the output as below.
bs_6

Without Bootstrap

  • You would not find any difference as the HTML page rendered normally, to make the HTML page with Bootstrap styling make sure you follow next step.
  • The key point here is, Bootstrap styles will take affect only if you wrap your HTML tags inside a <div> with class name “container”
    • ‘container’ is the Bootstrap css class name.

bs_8

  • Lets move <h1> tag inside <div class=”container”> and run the HTML page, which renders as below with more vibrant.
bs_7

With Bootsrap

Notes:

  • Bootstrap requires jQuery, hence jQuery file CDN reference comes with Bootstrap ‘Starter Template’
  • You would also get “popper.min.js” in the Bootstrap ‘Starter Template’, which is useful to show pop over notifications.

In the followup articles, we will see the Bootstrap styling of different controls.

🙂

Categories: Bootstrap Tags: , ,

[Dynamics CE] – Strange Plug-in issue due to the usage of global variables

December 26, 2018 Leave a comment

Other day, one of my colleagues reported a plug-in issue which could not be reproduced consistently. All the troubleshooting options (i.e., Plug-in Profiler, Tracing) had been used but was unable to found the root cause.

On close retrospection of code, we found out the usage global variables in Plug-in class file, which made the Plug-in ‘Stateful’.

Due to this, issue could not be reproduced when tested with Plug-in Profiler as it creates single Plug-in instance. Issue will only be reproduced when concurrent users instantiate plug-ins.

You have to make sure to create your Plug-in as ‘Stateless’ to avoid issues during concurrent Plug-in execution.

What is ‘Stateful’ Plug-in?

  • If the Plug-in ‘Execute’ method refer any global variable(s), makes the Plug-in ‘Stateful’.

public class CustomersVirtual : IPlugin{

// ‘context’ variable declared as Global
IPluginExecutionContext context = null;
EntityCollection results = new EntityCollection();
public void Execute(IServiceProvider serviceProvider) {
context = (IPluginExecutionContext)serviceProvider.GetService(typeof(IPluginExecutionContext));

if (context.MessageName.ToLower() == “retrieve”){
Entity customer = new Entity(“raj_virtualcustomer”);
customer[“raj_customersid”] = Guid.NewGuid();
customer[“raj_name”] = “ABC Corporation”;

//add it to the collection
results.Entities.Add(customer);
}

In the above Plug-in sample, variables ‘context’ and ‘results’ been defined as global and referred in ‘Execute’ method which makes it ‘Stateful’

What is ‘Stateless’ Plug-in:

  • If the Plug-in ‘Execute’ method, has its own local variables and does not refer any global variables make the Plug-in ‘Stateless’.

public class CustomersVirtual : IPlugin{
public void Execute(IServiceProvider serviceProvider){

// ‘context’ variable declared as Local variable
IPluginExecutionContext context = (IPluginExecutionContext)
serviceProvider.GetService(typeof(IPluginExecutionContext));

EntityCollection results = new EntityCollection();

if (context.MessageName.ToLower() == “retrieve”)
{
Entity customer = new Entity(“raj_virtualcustomer”);
customer[“raj_customersid”] = Guid.NewGuid();
customer[“raj_name”] = “ABC Corporation”;

//add it to the collection
results.Entities.Add(customer);
}

In this sample, variables ‘context’ and ‘results’ been defined as Local in ‘Execute’ method which makes it ‘Stateless’

Why ‘Stateless’ Plug-in is recommended?

  • As per the design, Dynamics platform caches plug-in class instances and hence the constructor is not called for every invocation of plug-in execution.
  • IPlugins should be stateless is that multiple system threads could execute the same, shared, plug-in instance concurrently.
  • This opens up members of classes that implement IPlugin to potential thread-safety issues which could lead to data inconsistency or performance problems.
  • Read-only, static, and constant members are inherently thread-safe and can also be used reliably within a plug-in class.

How the Dynamics platform Caches Plug-in?

  • For performance reasons, Dynamics DOES NOT dispose of the object after it completes execution.
  • Dynamics caches the object and calls Execute on the same object instance on the next activation of the plug-in.
  • Certain operations, such as changing a plug-in’s registration properties, will trigger a notification to the platform to refresh the cache. In these scenarios, the plug-in will be reinitialized..
  • This means that you need to be very careful when defining class-level variables in the plug-in class as multiple threads can execute the code at one time

Bottom line:

  • Don’t use Global variables in Plug-ins

Refer below articles for more insights:

🙂

Categories: CRM, Plug-Ins Tags: , ,

[Logic App and HTTP Request Trigger] Create a record in D365

December 20, 2018 Leave a comment

We got an ask from client that they should be able to Insert contacts in D365 from their Java application and requested our help.

To fulfill the ask, one option would be configuring S2S authentication so that Java application can connect to D365 using ADAL library and insert contacts.

Another option is using “Logic App” with “Http Request Trigger”.

High level approach:

  • Create a Logic App with ‘When a HTTP request is received’ trigger
  • Pass Contact record information in Json format as Request
    • Use ObjGen site to generate desired Json data.
    • This site seamlessly generates Json data based on our input. As I am going to create a Contact record, I generated below JSon data.

LogicApp_3

  • From Logic App, read the Json data and create Contact record using D365 connector
  • Finally capture the created Contact GUID in ‘Response’

Lets see the step by step approach to create Logic App and test.

Pre-requisites:

  • Dynamics 365 instance. Subscribe for trail if you have’t already
  • Azure Subscription.Subscribe for trail if you have’t already

Once you got the D365 and Azure Portal subscriptions below are the steps to create LogicApp.

Create a Logic App:

  • Connect to your Azure Portal and create a new ‘Logic Apps’. Refer article for steps to create Logic App.
  • From the list select ‘When a HTTP request is received’ trigger

LogicApp_4

  • In the next screen, click on “Use sample payload to generate schema” to generate the Json schema.

LogicApp_5

  • Paste the Json format prepared in ObjGen site

LogicApp_6

  • Click on ‘Done’ so that LogicApp generates “Request Body jSON Schema”

LogicApp_7

  • Next, we need to connect to D365 to save the Contact

LogicApp_8

  • Click ‘New Step’ and select ‘Dynamics 365’ connector. From the ‘Actions’ select ‘Create a new record’ and provide credentials and connect to your Instance

LogicApp_9

  • From the ‘Entity Name’, select ‘Contacts’
  • Map the Contact entity fields with the fields from ‘Dynamic content’ popup.
    • As ‘Company Name’ is a Look up to ‘Account’ entity, make sure you map
      • ‘Company Name Type’ = ‘accounts’
      • ‘Company Name’ = ‘id’ passed from Json

LogicApp_10

  • Next we need to capture the ‘Response’, choose ‘Response’ from ‘Actions’

LogicApp_11

  • In the ‘Response’ control,
    • In the ‘Headers’, add ‘Content-Type’ as key and ‘application/json’ as Value.
    • In the ‘Body’, form your output string and ‘Contact’ field from ‘Dynamic Content’ to capture the GUID

LogicApp_12

  • Save the Logic App

Test the Logic App:

  • Copy the “HTTP POST URL” from the “When a HTTP request is received” control.

LogicApp_13

Using Post Man:

  • Create a ‘POST’ request and paste the URL copied from Logic APP
  • In the ‘Headers’, add ‘Content-Type’ as key and ‘application/json’ as Value.

LogicApp_14

  • In the ‘Body’, paste the Json (You can copy the Json format prepared in ObjGen site)
  • Click ‘Send’ to call Logic App and capture the Response.

LogicApp_2

Using jScript and HTML:

  •  Below the jScript to call the Logic APP URL by passing JSon and capture the response

<html lang=”en” xmlns=”http://www.w3.org/1999/xhtml”&gt;
<head>
<meta charset=”utf-8″ />
<title>Test Logic App</title>

function TestLogicApp() {
try {
var xhr = new XMLHttpRequest();
var url = “Logic App URL“;
xhr.open(“POST”, url, true);
xhr.setRequestHeader(“Content-Type”, “application/json”);
xhr.onreadystatechange = function () {
if (xhr.readyState === 4 && xhr.status === 200) {
alert(xhr.responseText);
}
};
var data = JSON.stringify({
“firstname”: “Rajeev”,
“lastname”: “Pentyala”,
“Account”: {
“id”: “A16B3F4B-1BE7-E611-8101-E0071B6AF231”,
“Name”: “A Datum Corporation”
}
});
xhr.send(data);
} catch (e) {
alert(“Error – ” + e.description);
}
}

</head>
<body>
<input type=”button” value=”Post” onclick=”TestLogicApp()” />
</body>
</html>

  • Open the HTML page and click the ‘Post’ button to capture the Response returned from LogicApp

LogicApp_1

Troubleshoot and track the history:

  • To troubleshoot and track the Requests, from the ‘Logic App’, click on ‘Overview’ and check under ‘Run history’

LogicApp_15

🙂

[MS Word] The Linked file isn’t available

December 19, 2018 Leave a comment

Other day, I was getting below “The Linked file isn’t available” pop-up, while opening a word document shared by client.

Word_1

Reason:

  • Word document has charts and graphs controls embedded, which were rendering based on the data from another excel sheet.
  • Excel sheet had configured as a linked file in the Word document
  • Since Excel sheet was not shared by client in the first go, Word document was showing “The Linked file isn’t available” popup.

Fix:

  • Once you got the link file (i.e., Excel sheet in my case), below are the steps to fix, if you are still getting the popup.
  • From Word document, click on File -> Info -> Related Documents -> Edit Links to Files

Word_2

  • In the ‘Links’ window, either click on ‘Change Source’ to correct the ‘Link file’ path or click ‘Break Link’ button if you want to remove the files link.

Word_3

  • Once the file paths are corrected, click on ‘Update Now’ to reflect the changes in Word document
  • Now, Word document should open with no “The Linked file isn’t available” pop-up.

🙂

Categories: Misc Tags: ,

[Log4net] Exception while reading ConfigurationSettings

December 16, 2018 Comments off

We were using Log4net logging framework to log exceptions in our web application and encountered below exception during the log:

Log4Net_1

Reasons:

There can be many reasons right from misplacing Log4net config settings to not loading the config file.

Fix:

Below is the step by step approach on how to use Log4net framework.

Install Log4net NuGet package:

  • From Visual Studio, open Tools -> NuGet Package Manager -> Manage NuGet packages for solution…

Log4Net_2

  • Search for ‘Log4net’ and install the package

Log4Net_3

Add configurations in App.config/Web.config:

  • In your App.config/Web.config file, add a new config section named ‘log4net’. Make sure <configSections> is the first node under root <configuration> node.
  • Add <log4net> node with details like Path where you would like to store the logs and other properties.
  • Your App.config/Web.config file looks as below:

<configuration>
<configSections>
<section name=”log4net” type=”log4net.Config.Log4NetConfigurationSectionHandler,Log4net”/>
</configSections>
<log4net>
<appender name=”General” type=”log4net.Appender.RollingFileAppender”>
<file value=”D:\log.txt“/> <!–Physical path to log files–>
<appendToFile value=”true”/>
<rollingStyle value=”Size”/>
<!– Specifies the number of files that will be written. This is an example for ten files. The files will be named engine.log.1, engine.log.2, engine.log.3, etc. –>
<maxSizeRollBackups value=”50″/>
<!– The File Size limit for each file. KB stands for Kilobytes, MB (MegaByte) is also an option. –>
<maximumFileSize value=”5MB”/>
<staticLogFileName value=”true”/>
<layout type=”log4net.Layout.PatternLayout”>
<conversionPattern value=”%date %-5level – %message%newline”/>
</layout>
</appender>
<root>
<appender-ref ref=”General”/>
</root>
</log4net>
<startup>
<supportedRuntime version=”v4.0″ sku=”.NETFramework,Version=v4.6.1″ />
</startup>
</configuration>

Using Log4net in your code:

  • We need to load the Log4net configurations defined App.config file in class file using below statement
    • Below statement can be either placed in your Class file or project’s “AssemblyInfo.cs” file

[assembly: log4net.Config.XmlConfigurator(Watch = true)]

  • Define LogManager Object using below statement

private static readonly ILog Log = LogManager.GetLogger(System.Reflection.MethodBase.GetCurrentMethod().DeclaringType);

  • Use Log.Info(“”) to log info and Log.Error(“”) to log exception details.
  • With above specified statements your class file looks as below

Log4Net_5

using log4net;

// Load Log4net configurations defined App.config file
[assembly: log4net.Config.XmlConfigurator(Watch = true)]
namespace Log4Net{
class Program{
// Define LogManager Object
private static readonly ILog Log = LogManager.GetLogger(System.Reflection.MethodBase.GetCurrentMethod().DeclaringType);

static void Main(string[] args){
try{
Log.Info(“Log Starts”);
// Throw error
throw new Exception(“Exception!!!!”);
}
catch (Exception ex){
Log.Error(“Error – ” + ex.Message);
}
finally{
Log.Info(“Log Ends”);
Console.ReadLine();
}
}}

  • Execute the logic and you should get a log file stored in specified location with logs

Log4Net_4

Refer article for Log4net best practices.

🙂

Categories: Misc Tags: ,