Thursday, December 27, 2012

Hosting images using Handler (ASHX)

In HTML, when we want to display images, we are using the following tag:

   <img src="images/myProfilePhoto.jpg"/>

That's very simple and has nothing much to complaint. But, you won't be able to trace who has requested the image file especially when the privacy issue comes into place... it becomes very nasty. In this case, we need to use ASP.NET Handler (ASHX) to host the images.

Advantage of hosting images through Handler:
  • You can hide the image file path. For example, your web app is located in D drive and all image files are stored in E drive (where you don't have to expose the image folder in IIS).
  • You may track down the visitor information that includes their IP address, browser, etc.
  • You may stored the images in a database and host it through the Handler - you don't need to create an image file physically and then write the phyicsal file name into "SRC" attribute. You just need to set the SRC attribute to your ASHX handler (refers to the sample code in the link below).
  • You may cache the images in the server.

In the HTML, you will have something like this:

  <img src="showPhoto.ashx?memberID=0001"/>

Where "showPhoto.ashx" is the Handler that you develop and "memberID" is the query parameter. Your handler should return the profile photo (in byte array) for member ID 0001.

For the code on how to implement the Handler or ASHX:

  http://stackoverflow.com/questions/994135/image-from-httphandler-wont-cache-in-browser
  http://stackoverflow.com/questions/1507572/streaming-databased-images-using-httphandler

For full explanations on the Handler:

   http://support.microsoft.com/kb/308001

Friday, December 14, 2012

Prevent the setting nested into sub-virtual directories

If you have a virtual directory which contains sub-virtual directories and you don't want the root virtual directory settings (in the web.config) to be inherited into the sub-virtual directories, you have to wrap the "system.web" with "location".

  <location path="." inheritInChildApplications="false">
    <system.web>
    ....
    </system.web>
  </location>

Tuesday, December 4, 2012

Looking for clue which website crash IIS

I have about 10 ASP.NET web applications running on the same IIS server. Somehow, I made changes to  "some" libraries and I could not figure out which web application keep crashing IIS server.

After many days in googling the solution, I found out that there is a freeware program which is able to open .WER file. Within this crash dump file, you will be able to find out which web application crashed your IIS.

   http://www.nirsoft.net/utils/app_crash_view.html

You will be surprise when you run this program because it will show all the crash dump files in your server/laptop.

Sunday, November 25, 2012

Enabled debugging log in .Net compiled app

To enable the log, change/add the following entries:

[HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Fusion]
"ForceLog"=dword:00000001
"LogFailures"=dword:00000001
"LogResourceBinds"=dword:00000001
"LogPath"="D:\\DebugLog\\"

Monday, November 19, 2012

Get client endpoint in WCF

Below is the code to get the client endpoint in WCF:

public string GetClientEndpoint()
{
    MessageProperties properties = OperationContext.Current.IncomingMessageProperties;
    RemoteEndpointMessageProperty endpoint = properties[RemoteEndpointMessageProperty.Name]
                                as RemoteEndpointMessageProperty;
    string s= string.Format("Client endpoint => {0}:{1}", endpoint.Address, endpoint.Port);
    return s;
}

In case you are developing a custom transport channel, please refer to the following article:

http://blogs.msdn.com/b/phenning/archive/2007/08/08/remoteendpointmessageproperty-in-wcf-net-3-5.aspx

Monday, October 22, 2012

Scaling out your system using web services

There are many different ways to improve the system respond time: one of the strategy is call scaling out. In our system design, we are implementing the "basic modules" (i.e., the system infrastructure) in web service and it is able to achieve this easily.

Web service does not have a huge different from a website. The noticeable different is that it does not have user interface (or web pages) for visitor to access. You may imagine that the web service like a mobile phone station/transmitter which is providing connection to the mobile phone. In .Net, the web service is implemented in ASMX format, WCF (Windows Communication Foundation) or simply ASPX (which returns the data in XML or JSON format).

Now, the best part of web service is not something that will make our solution cool. Instead, it is able to scale out to a server other than the web server (that is hosting the website). In this case, our customer might end up with a web server to host the website, a few web servers that host the web services.

Many programmers argue that web service is slow because of XML SOAP involves in the communication. It's true that web service in ASMX is slow but the visitor won't really feel it because of these communications were made among the web servers which is sitting next to each other. Of course, the web service implemented in XML SOAP is not suitable for real-time application. The real-time application requires low level socket programming and the handling strategy will be different.


Monday, October 15, 2012

Security web service

When you are developing a large scale application, you need a security module that is able to authenticate the users. In our system design, we developed a security web service which is shared among the sub-modules and also reduce the development time.

In .Net, you can achieve this with the technology that you want:
  • Implementing the security service using ASMX/ASHX - this service will be hosted through HTTP/HTTPS.
  • Implementing the security service using WCF - in this case, you will have the choices of different protocols such as TCP, named pipe, etc.
If you are asking why we need to reinvent the wheel when .Net comes already have this security feature for enterprise? The answer is simple: our security web service can be tailored made based on our customer's requirements. We know that not all projects that we are involving requires a complex security service. Some requires a basic login with user name and password only. Some requires the security control upto field on the screen.

Updates on 6th May 2017 - it seems like ASMX or WCF are quite hard to be converted to other programming language/platform. Best is to use ASHX (i.e., generic handler) which has a faster response time due to it's simplicity and  flexibility. It's also easier to port over to other programming language/platform.

Monday, October 8, 2012

Security design consideration for web application

The security problem with web application:

  • Web application is easier to hack as long as you know the URL - this means that some security control must be implemented in the web application.
  • The primary key value of the table is integer data type - this is easier to guess what's next value. For example, "http://myWeb.com/customer.aspx?cust_id=123" and the next record is "http://myWeb.com/customer.aspx?cust_id=124".
  • Session ID - you may rely on the ASP.net session ID or you handle it your own.
  • Deleting record with JavaScript confirmation and then fire AJAX call to the delete action URL - is this secured? Does the delete action page implemented sufficient control?
  • Folder with read & write permission for user uploading file - without limiting the file type that is acceptable by the web application, your website will have a security hole that can be exploited.
  • Audit log should include the browser type, URL referrer and also the user's IP address. Without these information, it will be impossible to track who has accessed which feature/data.
My question is that do you have all your ASPX web page inherit from your custom page class or System.Web.UI.Page class? If you are using the later, then, you are letting your programmer to implement all kinds of security control that might have security loop hole.

Monday, October 1, 2012

Security check point


In Windows client, you can develop a static function call SecurityCheckPoint() that gets the user ID and password. This SecurityCheckPoint() method will be very useful whenever you want the user to re-authenticate before any process start OR you want to get the supervisor authentication.

Well, this can be useful for the web application as well but you need to implement it using JavaScript that show a modal dialog and AJAX calls for authentication.

Tuesday, September 25, 2012

Something about user access control or security control design

Below is a few strategy to implement the user access control or the security feature in your application.

  1. The simplest design will be user name + password and stores these information in a database table. No control over the feature accessibility.
  2. One level harder will be using one security "action" to treat as one permission. And one security action represent a menu option, button, input field, display field or a process to be executed. This design requires 1 user class and a collection of permitted/allowed security actions. So, you need two database tables to stores the information. For example, user A allows issuing and editing invoice but not deleting any invoice. In this case, you will have 3 allowed actions (or record) for user A.
  3. In case you feel that having one security action mapping to the feature is cumbersome and require lots of hard space, you may consider adding a flag field in the security action. For example, "Invoice" action will have 3 flags: issue, edit and delete where the "flag" is in BIT data type (in MSSQL database). If the flag value is "1" means permitted and "0" means not permitted.
  4. Some applications requires another level of sophistication - that is using "user level" in conjunction with the security actions.
  5. Another kind of implementation is to have write level (0-10) and read level (0-10). Both values are use in conjunction with the menu option and input fields. For example, the credit limit field for the customer has read level of "5" and write level of "8". If the user's read level is "5" and the user will be able to view the credit limit field. If the user's write level is also "5", then, this credit limit value will be disabled from editing. 
So, which one is better? It's all depend on your need. As for us, we prefer #2 due to easier to implement and future enhancement. It's also very easy to cater for changes.

Let's assume that you read the previous article, the CUser class will have a CanAccess() method which returns true or false. The application should check the result of this method before performing the process/action whereas CUser class.

Different flavor of CanAccess()
  • bool CanAccess(Guid action_id)
  • bool CanAccess(Guid action_id, PermissionEnum permission) [PermissionEnum {insert, update, delete, select]
  • bool CanAccess(Guid action_id, int user_level)
  • bool CanAccess(int read_level, int write_level)

Thursday, September 20, 2012

Reusable class - user access control

This is another important area in the systems and it is reusable as long as the design is generic to cover all possible combination.

Basically, it should meet the following requirements:
  • Security control - allows user to logon to the system and verify their user name and password.
  • Access permission - permission could be controlled by menu level, screen level and field level (whether the field is show/hidden or enable/disable).
  • User access log - this is compulsory for audit purpose and also the alert.
  • Access deny alert - upon hitting certain number of invalid user name or password, the system should generate alert and email it to the system administrator.
  • Password policy - you may consider to implement minimum password length and password complexity.
  • Allow supervisor overriding - this can be useful when the current user does not have permission to access certain feature (such as edit customer address) but requires to do so.
  • In case the system is a web base system, it should store the browser type and visitor IP address for audit purpose.
 You need the following classes to support the above mentioned requirements:
  1. CUser - this class stores the user information such as user name, password, email address, etc.
  2. CAction - this class stores all the permissions (or features) for the system.
  3. CUserAccessLog - this class responsible for keeping track the user login and logout activities.
  4. CLog - this class (which has been discussed in previous article) which is responsible for storing the audit information such as which "action" (or "featuer") the user has clicked.
For the detailed implementation, you might have work it out by yourself.

Monday, September 3, 2012

Reusable class - System log - the information for troubleshooting

In our system design, we are trapping all the exceptions that raised up at runtime and store it into a central database. This allows us to provide faster response time in fixing the error before the user complains. I know many people will ask why there is an error and why it was not catch at the development or testing phase. The answer is simple, we are not developing standard package. Almost all projects come with different requirements except for the "infrastructure" (such as the security, application log, etc).

To log down the exception, this error logging process should done in a very short time so that it won't affect the system performance or other processes. This can be achieve by saving the exception using a different thread.

In our system logging class, we have the following methods:
  • AppendLog - this save the log as "audit log".
  • AppendError - this save the exception and the failure point as "error".
  • AppendWarning - this save the log as "warning" and it is very useful when the system setting is missing or misconfigure.
To track the failure point, refer to System.Diagnostics.StackTrace class.
To save the log information in another thread, refer to System.Threading.ThreadPool.

Our application log table design:

http://sqllauhw2000.blogspot.com/2012/07/you-need-application-log-for-your.html

Tuesday, August 28, 2012

Executing a process periodically in Windows


There are many types of application running in an enterprise. One of it is called the "nightly job" (i.e., the job that runs periodically) which is running on every night. On the other hand, some of the jobs is running hourly, weekly or monthly.

In our experience, the main issue in running a process periodically is that "schedule" itself. Consider this:
  • The simplest schedule job - run the job every night.
  • Run the job once for every hour, week, month or year.
  • Run the job once for every hour, week, month or year between 10AM to 6PM.
  • Run the job on every Monday, hourly between 10AM to 6PM.
This is complicated and requires lots of testing if you are creating your scheduler program. Instead, the better way is to utilized the Task Scheduler that comes with Windows. This is what you have paid for.

Below is the screen snapshot of where you can find the Task Scheduler.




Below are a few ways to execute a job/process periodically in Windows:
  1. Develop a Windows Service - add a System.Threading.Timer class and execute the callback periodically. With Timer class, it is able to run the process repeated in the same interval. If you want to run the next callback in different timing, you will have to calculate the interval and call Change() which will be complicated (depends on your need). Another problem that might arise is how to include the dependencies (or DLL)? For example, you need to generate daily report in PDF format and email it to the bosses.
  2. Develop a program (.EXE) and schedule it in the Windows Task Scheduler - this is simple and clear cut. With this option, it solves the scheduling problem. But, it does not solve the dependencies problem as mentioned above.
  3. Develop a web page which execute the process in a different thread and schedule it in the Windows Task scheduler - another requirement for this option is that it requires a small program which will call the URL (using System.Net.HttpWebRequest class) and pass the URL as the command line parameter. This solves the scheduling complexity (which handles by the Windows Task Scheudler) and also the dependencies (where all the business processes/rules are stay in the ASP.NET website). Of course, if the business processes/rules were in the Windows Client EXE, you will have no choice but fall back to strategy #2 as mentioned above.

Monday, August 20, 2012

Reusable custom web control

When you are building web application, blog site, forum, shopping cart, etc, often, there are some information in "div" will be reuse throughout the website or reused in selected pages. To avoid writing the HTML tag again and again, you may consider using the custom web control.

To create custom web control, right click on your web project and choose Add New Item. Then, choose Web User Control (i.e., System.Web.UI.UserControl class). Web user control is able to utilize the HTML designer in Visual Studio. So, you will be able to complete the design in a shorter time.

Another way to create custom control is to writing codes by declaring a new control which inherits from CompositeControl or WebControl. But it does not support any visual designer. The biggest challenge is for the graphic designer to touch up the design in C#/VB.Net code because they are not the programmer.

Advantage of using UserControl:

  • Easily separate the JavaScript from the web page.
  • Easily moving the control around the web page.
  • Easier to test the custom web control.
  • Easier to share the same control in different design style with other projects.
  • Easier to maintain the design with or without using CSS file.
  • Reduce the complication of HTML tags within a page.

When to use it?

  • You have to display "modal dialogue" box in the page which requires JQuery dialog. This dialog requires a "div" for the dialog and also contains the many data entry fields.
  • The "compulsory" aster rick marker in red color.
  • The "last updates", "news" or "events" section.
  • The banner for header and footer.
  • Application menu.

Tuesday, August 14, 2012

Should I develop a custom control or just add it to the form

The definition of "reusable control":
  • The control will be reused in many areas in the same project - for example, "customer group" drop down list which can be reused in many screens within the same project.
  • The control will be used more than once in a project and also useful in other project - for example, DevExpress has developed xtraReport which can be reuse in many projects.
  • The control will be used only once in a project and also useful in other project - for example, you have developed a "main menu" control which reads the menu options from XML file.
In order to speed up the development, testing, implementation and maintenance, you are advisable to come out with a custom control and then drag it into other custom control or Form.

Tricks for using custom control:
  • Drag the custom control on a MDI child Form - in this case, you control will always sit inside the MDI parent window.
  • Drag the same custom control on a non-MDI child Form - in this case, you can shown the control modally.
  • Drag the same custom control into a Tab page control and show it in any Form - now, you custom control will be act like a tab page.
  • Another rare situation is that you instantiate this custom control at runtime and position it to the appropriate location. By doing this, you don't have to mess up the parent control/Form. The coding will be very clean and precise.

Tuesday, July 31, 2012

Designing reusable control Part 2 - designing composite control

Of course, when things are simple, you can always try to look for the best available control and create a child class from it. But, in real life, you won't always get the easiest job. This is the time that you need more than inheritance from the object oriented programming.. the composite control.

Steps to develop a composite control using UserControl
  1. Right click on the project.
  2. Choose Add new item.
  3. Select UserControl.
  4. Then, drag the necessary controls from the common control section into the UserControl that you have just added.
  5. Start writing some codes for this new UserControl. Of course, the most important will be loading data, validating user input and saving data. Another piece of code that is helpful is called "RefreshUI" which is responsible for controlling what should be hide or show on the screen base on the parent form/control. You might consider to add this method into your UserControl.
As simple as that, you have a composite control. Well, you can google for tutorial on the detailed steps with nice print screen. Sorry, I'm not going to repeat it. What I plan to do is to explain when do we need this?

From my experience, it seems many developers especially fresh graduate they "know" UserControl but "never use" it. Below is some example from live experience:
  • My customer asked me to develop an attendance grid which displays all the check-in guests. So, I started with "attendance item" control which displays the guest's photo + name. Then, I developed another control call "attendance grid". Finally, I developed "attendance" control which relies on both attendance item and attendance grid.
  • The situation gets complicated when you have domestic guests and international guests. These guests are using different "identity card" and the identity number are handled in different way. So, we develop a UserControl which is able to capture both domestic and international identity  number. This control is then reused in many of the screens.
  • We also develop a composite control to show the necessary options for the user for generating report.
  • Application menu is the composite control that will be reused in all projects.

Tuesday, July 24, 2012

Designing resuable control

Before we start the coding in any project, we have to identify the reusable screen, part of the screen or a group of fields. In this stage, we are developing custom control to be reuse in one or more projects.

Below is the reasons of developing custom control:

  • To reduce the overall development time - in Visual Studio, the custom control can be drag from the Toolbox and drop onto any WinForm or UserControl. Note: the custom control that you have added to the project will appear in the Toolbox after you have compiled the project or solution (if your custom control is residing in other project).
  • To reduce the testing time - this requires test once only because the control is reusable.
Below is the situation where you need to design a reusable control:
  • You are working on system that requires to capture "record status" which is used in many screens. 
  • The user might request for enhancement on this input control but the enhancement is not an urgent priority now
  • You are splitting the system into multiple small section to be handle by different programmer.
For example, in your system, there is a field that occur in many screens and it is called "status". It contains 4 statuses.In this case, you may add a new Class into the project and then set the base class (or parent class) to "ComboBox". It has a method name RefreshData which is responsible for loading the available statuses (which could be from database and it's up-to your design).
public class StatusComboBox : ComboBox
{
    public void RefreshData()
    {
        this.Items.Clear();
        this.Items.Add("Pending");
        this.Items.Add("In Progress");
        this.Items.Add("Completed");
        this.Items.Add("Cancelled");
    }
} 
After you have compiled the project, the StatusComboBox custom control will appear in the Toolbox. Below is the screen snapshot of the Toolbox:



Now, you may drag this control onto the Form and call "statusComboBox1.RefreshData()" to load the items.

Tuesday, July 10, 2012

Splitting the big piece into small pieces

Whenever you get a project, don't be so excited and start writing codes. Below is some guidelines that helps you in managing the project development. Please take note that this article is not covering the entire SDLC (system development life cycle).

Development flow:
  1. Ask for the sample reports and forms.
  2. Designing the database - add the standard table structures such as security module, session table, etc. Then, follow by the new table structures.
  3. Design the screen flow chart - you have to decide how many screens to the develop and the flow from one screen to another.
  4. Identify the reusable class that can be shared with other project.
  5. Identify the reusable custom control - most of the times, the screen (i.e., WinForm or WebForm can be splitted into multiple controls and then combine all the controls into one screen). This is very useful but requires thorough knowledge on the OOP (object oriented programming).
  6. Design the screen layout.
  7. Identify the shared functions - for example, the function to read the system settings out from the database or flat file.
  8. Designing the report layout - the user might pass you the hard copy of reports. But, sometimes you might have to propose new format (in digital format) that includes the chart/graph to show the summarize data.
  9. Start developing the system - now, you may start writing codes. I know you are waiting for this great moment.
  10. Fine tuning the screen flow - some users might not understand why you have to design the screen in this or that way. So, you might have to fine tune the screen to reduce the support calls and training time. This is a very important step where most of the projects might failed here.
  11. Fine tuning the field flow - this requires the feedback from the user where you might not have the full knowledge of the business.
  12. Fine tuning the menu options - some of the menu option can be remove and replace by shortcut button or popup menu.
  13. Add shortcuts or popup menu - I know this is not critical to any system but you should always do this. Most of the users will appreciate your effort in this area and this is the surprises when they found out there is an easier and convenient way to do their job. For example, the user may press the Delete key or right click and choose Delete in order to delete the selected files in Windows Explorer.
  14. Fine tuning the query response time by add appropriate indexes or using multi-thread - this is especially loading lots of records from the database or generating reports. Do you know how frustrated is that for the user to see "not responding" word appear in the program/task manager?
Assumptions:
  1. Always assume that you are not sure about the detail process - so ask for all the details and do not assume what you know is correct.
  2. Always assume that the user still have something exceptional procedures to follow - well, you have to prepare yourself before interviewing the users.
  3. Always assume that the user will request for changes in the database or system flow - this requires declaring constants or reading the settings from the database, writing modular program, passing the parameter with an object type instead of value type, etc.
  4. Always assume that the data will grow faster than the user is expecting - when the system has rolled out, it will grow faster than you are expected. The proper way to handle this is to calculate the number of transactions per week/month that will be entered into the database. Then, estimated the number bytes per transactions. Base on the total bytes that requires, you will be able to come out with an appropriate server/workstation specification.
 Is that all? NO. You have to learn from experience or from other experts and then build your own checklist.

Thursday, June 28, 2012

Running different codes between debug mode and release mode

This is one of the compiler feature that is not widely used or not known by most of the programmers. For example, in ASP.net, you might want to use the full Java Script file in the debug mode. But, in the release mode, you might want to include the "light" version (or minified version). This is because the minified version requires lesser time for the browser to download it.

public void IncludeScript()
{
    Page pg = HttpContext.Current.Handler as Page;
    string js_url;
    string key = "jquery";

    if (!pg.ClientScript.IsClientScriptIncludeRegistered(key))
    {
#if DEBUG
       // for debug mode, include the full JavaScript.
        js_url = pg.ResolveUrl("~/js/jquery-1.7.1.js");
#else
       // for release mode, include the minified version.
        js_url = pg.ResolveUrl("~/js/jquery-1.7.1.min.js");
#endif

        pg.ClientScript.RegisterClientScriptInclude(pg.GetType(),
                                                    key,
                                                    js_url);
    }
}

Other situation where you might want to use this concept:

  • Set the default user name and password in debug mode.
  • Get and/or save the runtime value in debug mode.
  • Create a debug log while debugging the program.
  • Modifying or setting variable's value at debugging time.

Please take note that the compiler directive does not limit to ASP.net. It is meant for all kinds of project types.

Saturday, June 9, 2012

Invoking a static method through reflection

For example, you have a program that requires to download the updated version from the Internet through an updater program. And this updater program is a standalone EXE program which was shared among other software projects.

In the main program, you may invoke the method provided in the updater program by calling InvokeMember.

public static bool RequiresUpdate(out Version latest_veresion)
{
 latest_veresion = null;
 string url = GetUpdateUrl();
 string info_file_name = GetInfoFile();
 
 AppDomain app_domain = AppDomain.CreateDomain("AutoUpdate.exe");
 Assembly asm = app_domain.Load(s);

 // get the class.
 Type type = asm.GetType("AutoUpdate.CAutoUpdate");

 object[] param = new object[]
      {
       url,
       info_file_name
      };

 // execute the static function
 string[] need_update = (string[])type.InvokeMember("CheckUpdateInfo", 
       BindingFlags.Default | BindingFlags.InvokeMethod, 
       null, 
       null, 
       param);

 if (need_update != null
  && need_update.Length > 0)
 {
  string[] v = need_update[0].Split('=');
  if (v.Length > 1)
  {
   latest_veresion = new Version(v[1]);
   Version current_version = Assembly.GetExecutingAssembly().GetName().Version;

   if (latest_veresion > current_version)
   {
    AppDomain.Unload(app_domain);
    return true;
   }
  }
 }

 AppDomain.Unload(app_domain);

 return false;   
}

Tuesday, May 29, 2012

Making Crystal Report 11 to work in IIS

For Crystal Report 11 to work in IIS, you might have to ensure that the web.config file contains the following entries:

<httpHandlers>
  <add path="CrystalImageHandler.aspx" 
    verb="GET" 
    type="CrystalDecisions.Web.CrystalImageHandler, CrystalDecisions.Web, Version=13.0.2000.0" />      
</httpHandlers>

<system.webServer>
<handlers>
  <add name="CrystalImageHandler.aspx_GET" 
    verb="GET" 
    path="CrystalImageHandler.aspx" 
    type="CrystalDecisions.Web.CrystalImageHandler, CrystalDecisions.Web, Version=13.0.2000.0" 
    preCondition="integratedMode" />
  </handlers>
</system.webServer>

Wednesday, March 28, 2012

Crystal Report + VS2010 (ASP.NET) -bobj is undefined

Below is the steps copied from this link.

1. You need to use Web Application Project,No Website Project because Web App will combine DLL to project also.
2. Copy C:\inetpub\wwwroot\aspnet_client\system_web\4_0_30319\crystalreportviewers13 (you'll got it when you install -CRforVS_redist_install_32bit_13_0.exe)   To your project such as  (ProjectName/crystalreportviewers13)
3. copy this below to your web.config
3.1
<configsections>
    <sectiongroup name="businessObjects">
      <sectiongroup name="crystalReports">
        </sectiongroup></sectiongroup></configsections>

<section name="rptBuildProvider" type="CrystalDecisions.Shared.RptBuildProviderHandler, 
CrystalDecisions.Shared, Version=13.0.2000.0, Culture=neutral, 
PublicKeyToken=692fbea5521e1304, Custom=null">
           <section name="crystalReportViewer" type="System.Configuration.NameValueSectionHandler">
      
3.2
 <businessobjects>
      <crystalreports>
        <rptbuildprovider>
          <add embedrptinresource="true">
        </add></rptbuildprovider>
        <crystalreportviewer>
              <add key="ResourceUri" value="/crystalreportviewers13">
      </add></crystalreportviewer>
      <crystalreports>
    </businessobjects>
Note: in case "/crystalreportviewers13" is not working, try to add "~" symbol.

3.4 Publish your web application with FTP Mode to your any folder,and copy this publish to your web server then TEST it!

My Note:
Another issue with the CR runtime installer is that it always install the necessary web files (such as javascript, icons, etc) to "C:\inetpub\wwwroot\aspnet_client\system_web\2_0_50727". So, if you changed your default IIS web folder to somewhere else, please make sure that you copy "crystalreportviewers13" from the above mention folder to your new IIS web folder.

Reference:
http://social.msdn.microsoft.com/Forums/en-US/vscrystalreports/thread/ef56f72b-7ede-47d8-ba9e-9e63b9ac0203

Monday, March 26, 2012

WebBrowser control tweak

You may tweak the WebBrowser control in case it does not binding to the latest IE version (ie, different from the installed IE).

Below is the registry to be modify:

[HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Internet Explorer\Main\FeatureControl\FEATURE_BROWSER_EMULATION]
"contoso.exe"=dword:00002328

The values for 'contoso.exe':

9999 (0x270F) - Internet Explorer 9. Webpages are displayed in IE9 Standards mode, regardless of the !DOCTYPE directive.
9000 (0x2328) - Internet Explorer 9. Webpages containing standards-based !DOCTYPE directives are displayed in IE9 mode.
8888 (0x22B8) -Webpages are displayed in IE8 Standards mode, regardless of the !DOCTYPE directive.
8000 (0x1F40) - Webpages containing standards-based !DOCTYPE directives are displayed in IE8 mode.
7000 (0x1B58) - Webpages containing standards-based !DOCTYPE directives are displayed in IE7 Standards mode.

References:

For discussion, see here:
http://stackoverflow.com/questions/4612255/regarding-ie9-webbrowser-control

For the MSDN reference, see here:
http://msdn.microsoft.com/en-us/library/ee330730%28VS.85%29.aspx#browser_emulation

Thursday, March 8, 2012

Extension method - BETWEEN function

Well, on and off we need to increase the readability of the code and also reduce the typo mistake in the comparison symbols. Here is how you can achieve it:

        public static bool IsBetween(this int value,
            int i,
            int i2)
        {
            return ((value >= i)
                    && (value <= i2));
        }
Now, you may write this code for the integer data type:
        int i = 5;
        if (i.IsBetween(1, 12))
        {
           // the value is between 1 and 12
        }
        else
        {
           // the value is out of range.
        }

By using extension method, you may create IsBetween() method for each data type and also your own data classes.

Tuesday, January 17, 2012

Convert Bitmap to Icon

This is quite easy to achieve by using the following procedure:

        public static Icon ToIcon(Bitmap bmp)
        {
            IntPtr i = bmp.GetHicon();
            Icon ic = Icon.FromHandle(i);

            return ic;
        }

Monday, January 9, 2012

Linq IN operator

Sometimes, you might want to extract the "intersection" of the two object lists but the object types are different. For example, you have a customer list and another one is invoice list. You want to get the customers whose "customer_id" exist in the invoice list. This can be done in the SQL syntax easily by using the IN operator. But, there is none in the Linq. So, I have written my own extension:

public static List<T> In<T, T2>(this List<T> list1,
           List<T2> list2,
           Func<T, T2, bool> predicate)
        {
            List<T> result = new List<T>();

           // exit immediately if list2 is empty or null.
            if ((list2 == null)
                || (list2.Count == 0))
            {
                return result;     // return blank list.
            }

            foreach (var item in list1)
            {
                if (list2.Where(n => predicate(item, n)).Count() > 0)
                {
                    result.Add(item);
                }
            }

            return result;
        }