Coding style: bools, structs or enums

April 11, 2008

Read an article about writing methods where you have to provide multiple boolean options for input:

http://blogs.msdn.com/kevinpilchbisson/archive/2007/11/30/coding-styles-bools-structs-or-enums.aspx

Instead of defining each option in the method signature:

Func1(boolean option1, boolean option2),

You can define a enum

OptionEnum {

  option1 = 0×1;

  option2 = 0×2;

  optionboth = (option1 | option2);

}

or Define a struct

 struct Option {

  bool option1;

  bool option2;

}

I agree with the author that it’s better to use Struct when you have lots of options and you have to define options for every possible combinations


Access UI thread objects from non-UI thread

April 10, 2008

Some articles which talk about how to change UI thread objects from non-UI thread

http://msdn2.microsoft.com/en-au/library/ms171728(VS.80).aspx

http://davebrooks.wordpress.com/2007/02/12/begininvoke-the-land-of-confusion

The function below demonstrates how to do access UI thread object from non-UI thread. When you want to set the button text from a non-UI thread, use button.InvokeRequired to check whether it is a UI thread. If it returns true (it’s a non-UI thread), calls SetText again using Form.Invoke. It would start the UI thread and the thread would be able to set the text property.

private void SetText(string text)
{
 
    // InvokeRequired required compares the thread ID of the
    // calling thread to the thread ID of the creating thread.
    // If these threads are different, it returns true.
    if (this.button1.InvokeRequired)
    {
 
        SetTextCallback d = new SetTextCallback(SetText);
        this.Invoke(d, new object[] { text });
    }
    else
    {
        this.button1.Text = text;
    }
}


throw vs throw ex

April 10, 2008

Find a good article explaining how to rethrow exception in .Net: http://weblogs.asp.net/bhouse/archive/2004/11/30/272297.aspx

To rethrow an exception in C# without losting the original stack trace info:

try {

}
catch
{
  throw;
}

To re-throw execption without preserving th original stack track:

try {

}
catch (Exception e)
{
 throw e;
}

 


writing web service for sharepoint

April 10, 2008

I need to create a Sharepoint web serivce at work. I follow the instructions from here but found it too long to read so I want to summarize the steps in here:

1. Create the web service. Register the dll into GAC by using gacutil /i dllname.dll. (If I don’t register dll into GAC it’s not working. I will just leave it for now and will investigate later).

2. Create the disco and wdsl file using this command from VS.Net command prompt:
Disco http://server_name:New_Port/Project_Name/Service_1.asmx

3. Rename service1.disco to service1disco.aspx. Open the file and replace this line:

<?xml version=”1.0″ encoding=”utf-8″?>

to:

<%@ Page Language=”C#” Inherits=”System.Web.UI.Page”%> <%@ Assembly Name=”Microsoft.SharePoint, Microsoft.SharePoint, Version=11.0.0.0, Culture=neutral, PublicKeyToken=71e9bce111e9429c” %> <%@ Import Namespace=”Microsoft.SharePoint.Utilities” %> <%@ Import Namespace=”Microsoft.SharePoint” %>
<% Response.ContentType = “text/xml”; %>

4. Rename Service1.wsdl to Service1wsdl.aspx and do the same thing to the file

5. Open Service1disco.aspx and locate

<contractRef ref=”http://server_name:New_Port/Project_Name/Service1.asmx?wsdl” docRef=
“http://server_name:New_Port/Project_Name/Service1.asmx” xmlns=”http://schemas.xmlsoap.org/disco/scl/” />

Change that to

<contractRef ref=<% SPEncode.WriteHtmlEncodeWithQuote(Response, SPWeb.OriginalBaseUrl(Request)
+ “?wsdl”, ‘”‘); %> docRef=<% SPEncode.WriteHtmlEncodeWithQuote(Response,
SPWeb.OriginalBaseUrl(Request), ‘”‘); %> xmlns=”http://schemas.xmlsoap.org/disco/scl/” />

6. Locate the tag:

<soap address=”http://server_name:New_Port/Project_Name/Service1.asmx” xmlns:q1=
“http://tempuri.org/” binding=”q1:Service1Soap” xmlns=”http://schemas.xmlsoap.org/disco/soap/” />

and change it to

<soap address=<% SPEncode.WriteHtmlEncodeWithQuote(Response, SPWeb.OriginalBaseUrl
(Request), ‘”‘); %> xmlns:q1=”http://tempuri.org/” binding=”q1:Service1Soap” xmlns=
“http://schemas.xmlsoap.org/disco/soap/” />

7. Open Service1wsdl.aspx and locate

<soap:address location=”http://server_name:New_Port/Project_Name/Service1.asmx” />

Change it to

<soap:address location=<% SPEncode.WriteHtmlEncodeWithQuote(Response,
SPWeb.OriginalBaseUrl(Request), ‘”‘); %> />

8. Copy the Service1wsdl.aspx file, the Service1disco.aspx file, and the Service1.asmx file to c:\Program Files\Common Files\Microsoft Shared\Web Server Extensions\ISAPI directory

9. Open c:\Program Files\Common Files\Microsoft Shared\Web Server Extensions\ISAPI directory\spdisco.aspx. Add the following line to the end of the file within the discovery element:

<contractRef ref=<% SPEncode.WriteHtmlEncodeWithQuote(Response, spWeb.Url + /_vti_bin/Service1.asmx?wsdl”,
‘”‘); %> docRef=<% SPEncode.WriteHtmlEncodeWithQuote(Response, spWeb.Url + “/_vti_bin/Service1.asmx”, ‘”‘);
%> xmlns=”http://schemas.xmlsoap.org/disco/scl/” /><soap address=<%
SPEncode.WriteHtmlEncodeWithQuote(Response, spWeb.Url + “/_vti_bin/Service1.asmx”, ‘”‘); %>
xmlns:q1=”http://schemas.microsoft.com/sharepoint/soap/directory/” binding=”q1:Service1Soap”
xmlns=”http://schemas.xmlsoap.org/disco/soap/” />

where binding=”q1:Service1Soap” specifiies the name of the class defined in the web service

10. try running the web service by entering http://sharepointserver_name:port/_vti_bin/Service1.asmx on the web browser.

Note:

1. When re-register gac, you have to restart IIS by typing iisreset
2. To debug web serivce locally from Visual Studio. Attach the the project to the workerprocess – w3wp.exe.


Principal Permission and Web Service Security

April 10, 2008

I am developing a Web Service and want to find a good way to authenticate and authorize users to use the service. I have looked into Role-Based Security Check and done some investigation on PrincipalPermission and Web Sevice Security. Here are the things I have found out so far:

PrincipalPermission

1 System.Threading.Thread.CurrentPrincipal.Identity stores the Identity of the Current Principal

2 Use PrincipalPermission declaratively – [PrincipalPermission(SecurityAction.Demand, Role ="Administrators")]. The downside of that is the Role have to be hardcoded to the attribute.

3. Use PrincipalPermission imperatively:

PrincipalPermission p = new PrincipalPermission(“user’, “role”);
p.Demand();

p.Demand() is checking that if the current principal (System.Threading.Thread.CurrentPrincipal) matches the principal specified by the current permission.

Web Service Security

1 ASMX web service is actually an ASP.Net application. It’s mapped to aspnet_isapi.dll. Therefore we can use ASP.Net security mechanism to authenticate and authorize web service.

2 When writing a web service, it’s better to inherit from System.Web.Services.WebService becuase the class provides direct access to common ASP.Net objects. There is a User property in this class that gets the ASP.Net server System.Web.HttpContext.User object and can be used to autenticate whether a user is authorized to execute the request

3 Select Authentication mode from ASP.Net Configuration Settings

4 If using Windows authentication, you can set the authentication scheme from IIS -> Directory Security -> Authentication and access control to control the authentication of the web service

5 You can also set your authentication mode in Web.config

6 Select “None” for authentication mode if you want to use custom authication

7 Do not use “Form” or “Passport” Authentication for web service as they needed redirection to the login page

8 You can use ASP.Net Authorization (e.g. use IIS or web.config) to handle authorization on Web Service. However, I think the downside of that is you can only control it in page level but not method level.

9 You can use .Net Role Security Check to hanlde authorization on Web Service. This way authorization can be handled in method level  

Good article for web service security: http://www.15seconds.com/issue/020312.htm

 


First post

April 10, 2008

My name is Felix and this is my first post.