Thursday, 30 September 2010

Create a new Outlook mail profile

It is quite natural that you want to create a new Outlook profile on client machine after Deepnet two factor authentication has been enforced on the Exchange server side.


The normal procedure of setup the profile will fail, as Deepnet OA agent won't be auto launched during the profile creation.



Technically speaking, the auto load feature is implemented as Outlook COM-Addin, the agent is only be launched after the profile is chosen. However the OA agent is a standalone Win32 application, you can start it at any time. In a word, you should manually launch it before adding a new outlook profile.


During the setup, do not click the button "Check Name", it is bound to fail.




Just ignore any error message and proceed to HTTP Proxy Setting




The first running of Outlook may look like freezed after you input the correct username and password, actually it is waiting for you to do some action! Please right click OA agent icon on taskbar,




and select the menu item "Restore". For example, it asks you to register the DevicePass token(see below)




Once the profile is fully created(it has connected to server and downloaded some emails), you can exit Outlook, also exit OA agent(right click the icon and choose Exit). Run Outlook again, this time OA agent should be auto launched(check the icon on the taskbar) when the usename/password dialog appears, if not, click Cancel,






then go to Trust Center and check if the agent is listed as an Active Application Add-ins



Monday, 27 September 2010

Install SharePoint 2010 RTM


Recently I needed a SharePoint 2010 to test Deepnet IIS agent. Deepnet requires web services working under form authentication, so I follow these two posts [1][2] which are pretty good(especially the first one). However, the installation(and configuration) still costed 2 days! so I am going to write down my story,just in case I'll forget it in the future. It also tries to ensure those people, who are trying to do the SharePoint form authentication with LDAP provider, do not suffer the same fate.


At the very beginning, I tried a standalone version of sharepoint 2010 which I thought was enough for me. The installation itself was quite straightforward, however, the "People Picker" never returned any AD user. My AD server was on another machine, so it was kind of remote LDAP access which I think it needed authentication, so I provided connectionUsername and connectionPassword,just like the one mentioned by this post.



<add name="membership"
type="Microsoft.Office.Server.Security.LdapMembershipProvider, Microsoft.Office.Server, Version=14.0.0.0, Culture=neutral, PublicKeyToken=94de0004b6e3fcc5"
server="192.168.222.200"
port="389"
useSSL="false"
userDNAttribute="distinguishedName"
userNameAttribute="sAMAccountName"
userContainer="CN=Users,DC=nanoart,DC=local"
userObjectClass="person"
userFilter="(&(ObjectClass=person))"
scope="Subtree"
otherRequiredUserAttributes="sn,givenname,cn"
connectionUsername="CN=administrator,CN=Users,DC=nanoart,DC=local"
connectionPassword="password" />

I doubled checked the connectionUsername and connectionPassword, in ADExplorer it worked without any problem. But in SharePoint People Picker, no luck at all.


This post suggested another format(not DN string) on connectionUsername and connectionPassword which I haven't got time to try. It points out, "One additional step is required and that is adding a couple of entries to the STS (Security Token Service) web.config file. You will need to add both connectionUserName and connectionPassword." If you are curious, please have a try yourself, and give me a feedback below.




<add name="membership"
type="Microsoft.Office.Server.Security.LdapMembershipProvider, Microsoft.Office.Server, Version=14.0.0.0, Culture=neutral, PublicKeyToken=94de0004b6e3fcc5"
server="192.168.222.200"
port="389"
useSSL="false"
userDNAttribute="distinguishedName"
userNameAttribute="sAMAccountName"
userContainer="CN=Users,DC=nanoart,DC=local"
userObjectClass="person"
userFilter="(&(ObjectClass=person))"
scope="Subtree"
otherRequiredUserAttributes="sn,givenname,cn"
connectionUsername="nanoart\administrator"
connectionPassword="password" />


I struggled for a few hours on that, eventually I gave up the standalone version, and decided to install SharePoint 2010 in a AD environment. Officially SharePoint 2010 is not recommended being installed on Domain Controller, so generally, you need 2 machines(see this post
for the details). Basically one machine(512M) for domain controller, another one(4G) to be a member server of the domain, and for deploying SharePoint.


I always want to make things simple, so I tried my luck to install everything (SharePoint 2010 plus SQL server 2008) on DC machine. Guess what? this time I wasn't disappointed. The installation was successful, and People Picker worked as well!



However another issue awaited me, which tortured me longer than the LDAP issue, I always got Access Denied error.



I believe I did right thing on User's Policy, as you can see this test user(i:0#.f|ldapmember|mingfa.ma) had "Full Read"(tried "Full Control" later as well).



This problem puzzled me for two days. I didn't realized that I fell right into the trap setup by myself until I saw this post.It mentioned somewhere that you need to set the default provider to our Forms provider, i.e. FBAMembershipProvider



OK let's look at how I modified the web.config of SharePoint site.




<membership defaultProvider="LdapMember">
<providers>
<!-- <add name="i" type="Microsoft.SharePoint.Administration.Claims.SPClaimsAuthMembershipProvider, Microsoft.SharePoint, Version=14.0.0.0, Culture=neutral, PublicKeyToken=71e9bce111e9429c" /> -->
<add name="LdapMember" type="Microsoft.Office.Server.Security.LdapMembershipProvider, Microsoft.Office.Server, Version=14.0.0.0, Culture=neutral, PublicKeyToken=71e9bce111e9429c" server="WIN-SPSRV.nanoart64.local" port="389" useSSL="false" userDNAttribute="distinguishedName" userNameAttribute="sAMAccountName" userContainer="CN=Users,DC=nanoart64,DC=local" userObjectClass="person" userFilter="(ObjectClass=person)" scope="Subtree" otherRequiredUserAttributes="sn,givenname,cn" />
</providers>
</membership>
<roleManager defaultProvider="LdapRole" enabled="true" cacheRolesInCookie="false">
<providers>
<!-- <add name="c" type="Microsoft.SharePoint.Administration.Claims.SPClaimsAuthRoleProvider, Microsoft.SharePoint, Version=14.0.0.0, Culture=neutral, PublicKeyToken=71e9bce111e9429c" /> -->
<add name="LdapRole" type="Microsoft.Office.Server.Security.LdapRoleProvider, Microsoft.Office.Server, Version=14.0.0.0, Culture=neutral, PublicKeyToken=71e9bce111e9429c" server="WIN-SPSRV.nanoart64.local" port="389" useSSL="false" groupContainer="CN=Users,DC=nanoart64,DC=local" groupNameAttribute="cn" groupNameAlternateSearchAttribute="samAccountName" groupMemberAttribute="member" userNameAttribute="sAMAccountName" dnAttribute="distinguishedName" groupFilter="(ObjectClass=group)" userFilter="(ObjectClass=person)" scope="Subtree" />
</providers>
</roleManager>

Below I list correct one, you can easily see what the difference is.



<membership defaultProvider="i">
<providers>
<add name="i" type="Microsoft.SharePoint.Administration.Claims.SPClaimsAuthMembershipProvider, Microsoft.SharePoint, Version=14.0.0.0, Culture=neutral, PublicKeyToken=71e9bce111e9429c" />
<add name="LdapMember" type="Microsoft.Office.Server.Security.LdapMembershipProvider, Microsoft.Office.Server, Version=14.0.0.0, Culture=neutral, PublicKeyToken=71e9bce111e9429c" server="WIN-SPSRV.nanoart64.local" port="389" useSSL="false" userDNAttribute="distinguishedName" userNameAttribute="sAMAccountName" userContainer="CN=Users,DC=nanoart64,DC=local" userObjectClass="person" userFilter="(ObjectClass=person)" scope="Subtree" otherRequiredUserAttributes="sn,givenname,cn" />
</providers>
</membership>
<roleManager defaultProvider="c" enabled="true" cacheRolesInCookie="false">
<providers>
<add name="c" type="Microsoft.SharePoint.Administration.Claims.SPClaimsAuthRoleProvider, Microsoft.SharePoint, Version=14.0.0.0, Culture=neutral, PublicKeyToken=71e9bce111e9429c" />
<add name="LdapRole" type="Microsoft.Office.Server.Security.LdapRoleProvider, Microsoft.Office.Server, Version=14.0.0.0, Culture=neutral, PublicKeyToken=71e9bce111e9429c" server="WIN-SPSRV.nanoart64.local" port="389" useSSL="false" groupContainer="CN=Users,DC=nanoart64,DC=local" groupNameAttribute="cn" groupNameAlternateSearchAttribute="samAccountName" groupMemberAttribute="member" userNameAttribute="sAMAccountName" dnAttribute="distinguishedName" groupFilter="(ObjectClass=group)" userFilter="(ObjectClass=person)" scope="Subtree" />
</providers>
</roleManager>


How ironic it is! I could only blame my "cleverness". When I edited the web.config file I thought I should comment out the original one, and made the inserted one as the default member(role) which eventually resulted in an agony of finding the exact reason.


I wonder if SharePoint had some troubleshooting measures to guide me to the right place quickly. To some extent, the error "Access Denied" in this case misled me, I am afraid to say so.



Reference


Step by Step SharePoint 2010 Install RTM



How to Set Up Novell eDirectory Authentication for Microsoft SharePoint



Setting Up SharePoint 2010 forms-based authentication for claims based web applications



Configuring Forms Based Authentication for SharePoint 2010 using IIS7

Wednesday, 22 September 2010

Add Deepnet two factor authentication onto SharePoint 2010


It is supposed that you can use Deepnet IIS agent to add 2nd factor authentication onto any web services hosted under Microsoft IIS. However it is doomed to fail on protecting SharePoint if you only configure the settings per its user guide.
Generally you will get the infamous “500 – Internal server error” when visiting the protected SharePoint site.



In addition, you may use IIS manager and check the authentication of the application “DasWeb”(under the protected SharePoint site) created by Deepnet IIS agent, you will get the following error message box which complains duplicate issues.




In order to make Deepnet work with SharePoint 2010, a little bit of effort needs to be contributed.


Prerequisites


You have to configure the SharePoint with Form Authentication before installing Deepnet IIS agent.


Changes on web.config of your SharePoint site


Please find the file web.config in your sharepoint site, you can use IIS Manger, select the site, then click “Explore” in Actions pane, open the file with your favourite editor.



  • locate <httpModules> under <system.web>, insert
    <add name="Session" type="System.Web.SessionState.SessionStateModule" /> after <httpModules>


  • <httpModules>
    <add name="Session" type="System.Web.SessionState.SessionStateModule"/>
    <add name="FederatedAuthentication" type="Microsoft.SharePoint.IdentityModel.SPFederationAuthenticationModule, Microsoft.SharePoint.IdentityModel, Version=14.0.0.0, Culture=neutral, PublicKeyToken=71e9bce111e9429c" />
    <add name="SessionAuthentication" type="Microsoft.SharePoint.IdentityModel.SPSessionAuthenticationModule, Microsoft.SharePoint.IdentityModel, Version=14.0.0.0, Culture=neutral, PublicKeyToken=71e9bce111e9429c" />
    <add name="SPWindowsClaimsAuthentication" type="Microsoft.SharePoint.IdentityModel.SPWindowsClaimsAuthenticationHttpModule, Microsoft.SharePoint.IdentityModel, Version=14.0.0.0, Culture=neutral, PublicKeyToken=71e9bce111e9429c" />
    </httpModules>

  • locate </modules> under <system.webServer>, insert
    <add name="Session" type="System.Web.SessionState.SessionStateModule" />
  • before </modules>




    <add name="FederatedAuthentication" type="Microsoft.SharePoint.IdentityModel.SPFederationAuthenticationModule, Microsoft.SharePoint.IdentityModel, Version=14.0.0.0, Culture=neutral, PublicKeyToken=71e9bce111e9429c" />
    <add name="SessionAuthentication" type="Microsoft.SharePoint.IdentityModel.SPSessionAuthenticationModule, Microsoft.SharePoint.IdentityModel, Version=14.0.0.0, Culture=neutral, PublicKeyToken=71e9bce111e9429c" />
    <add name="SPWindowsClaimsAuthentication" type="Microsoft.SharePoint.IdentityModel.SPWindowsClaimsAuthenticationHttpModule, Microsoft.SharePoint.IdentityModel, Version=14.0.0.0, Culture=neutral, PublicKeyToken=71e9bce111e9429c" />
    <add name="DasIIS7Native" />
    <add name="Session" type="System.Web.SessionState.SessionStateModule"/>
    </modules>


  • search “enableSessionState”, it will take you to somewhere



  • <pages enableSessionState="false" enableViewState="true" enableViewStateMac="true" validateRequest="false" pageParserFilterType="Microsoft.SharePoint.ApplicationRuntime.SPPageParserFilter, Microsoft.SharePoint, Version=14.0.0.0, Culture=neutral, PublicKeyToken=71e9bce111e9429c" asyncTimeout="7">

    make a change on enableSessionState, keep others intact.



    <pages enableSessionState="true" enableViewState="true" enableViewStateMac="true" validateRequest="false" pageParserFilterType="Microsoft.SharePoint.ApplicationRuntime.SPPageParserFilter, Microsoft.SharePoint, Version=14.0.0.0, Culture=neutral, PublicKeyToken=71e9bce111e9429c" asyncTimeout="7">

  • find <trust level="WSS_Minimal" originUrl="" />, comment it out


  • <!-- <trust level="WSS_Minimal" originUrl="" /> -->

  • save the file.

  • For your convenience, I uploaded the one in my lab just for the reference. Please do NOT use it to overwrite yours.


    Changes on web.config of the application “DasWeb”


    Simply download the file from here to overwrite the original one.

    Application Pool on the application “DasWeb”


    The application pool of DasWeb must be as same as the one of the web site root




    Now you should be able to use Deepnet two factor authentication with SharePoint 2010.




    Reference


    Configuring claims and forms based authentication for use with an LDAP provider in SharePoint 2010



    Configuring Forms Based Authentication in SharePoint 2010

    Friday, 6 August 2010

    Activate Token - script practice on Deepnet Authentication Server (< 5.0)

    This is a piece of code for activating all inactive tokens in token stock.

    import base64
    import xmlrpclib
    import sys

    def main():
    global server

    if len(sys.argv)==1:
    print 'Usage: acttoken serveraddr [port] [ssl]'
    print '\tdefault port = 8080'
    print
    sys.exit(1)
    addr = 'localhost'
    if len(sys.argv)>1:
    addr = sys.argv[1]

    port = '8080'
    if len(sys.argv)>2:
    port = sys.argv[2]

    proto='http://'
    if len(sys.argv)>3:
    if sys.argv[3]=='ssl':
    proto='https://'

    serverurl = proto + addr + ':' + port + '/das/xmlrpc'
    print serverurl
    server=xmlrpclib.Server(serverurl)

    result = server.das.listStockTokens({'status':'INACTIVE'})
    if result[0]!='OK':
    print "Error:", result
    sys.exit(2)

    tokens = result[1]

    for t in tokens:
    print t, server.das.enableToken(t, True)



    if __name__ == '__main__':
    main()

    Send Token - script practice on Deepnet Authentication Server (< 5.0)

    If you are using Deepnet two factor authentication server, probably you will agree with me that you can do almost everything with its management console. However, sometimes you may wonder if they provide script to do the trivial and repeatable job. Yes, they do, you can use python script to instruct the authentication server.

    Here it is an example of sending token.


    import base64
    import xmlrpclib
    import sys


    def main():
    global server
    addr = '192.168.222.149'
    port = '8080'
    proto='http://'

    serverurl = proto + addr + ':' + port + '/das/xmlrpc'
    print serverurl
    server=xmlrpclib.Server(serverurl)
    r = server.das.sendToken('77004280', False, 'SMTP')
    ##Use 'SMS' to send token by SMS
    print r
    return

    if __name__ == '__main__':
    main()

    Monday, 2 August 2010

    icon dimensions (0 x 0) don't meet the size requirements

    I tried to upload the binary of my updated iphone app, and found Apple forced us to use Application Loader instead of the original iTunesConnect.

    With the new approach, I got the following error

    iPhone/iPod Touch: Icon.png: icon dimensions (0 x 0) don't meet the size requirements. The icon file must be 57x57 pixels, in .png format

    I double-checked the image file, the size IS 57x57. I was puzzled, as it had no problem before(with iTunesConnect).

    Luckily, I found the following link on Internet

    http://www.iphonedevsdk.com/forum/iphone-sdk-development/54784-icon-dimensions-0-x-0-dont-meet-size-requirements.html

    where tonymy suggested

    Edit Project Settings -> Build -> uncheck Compress PNG Files


    As you can imagine, this glitch is not hard to avoid. I always try not to make a fetish of Apple's products, as I believe nobody is perfect.

    Next time, Apple should submit their applications to get our approval before publishing, just as our apps have to wait to be approved.

    Sunday, 1 August 2010

    xcode build error

    I haven't touched iphone development for one year. Today I have to update my app which has some problem on iphone OS 4.x, however I got a mystery when I rebuilt the project after renewing the iphone development certificate.

    Command /bin/sh failed with exit code 1
    Justis Publishing Ltd:no such identity Line Location Tool:0




    I have to admit that I did try this code sign certificate(Justis Publishing Ltd) last year before I opened an account with Apple (costed $99), and this cert was expired, so I deleted it in Keychain.

    I am quite sure I chose the correct development certificate which was downloaded from my account on iphone development portal. In XCode IDE, I poked around every corner, but failed to get rid of this error.


    My gut feeling told me this problem lied in the project setting, so I decided to have a look with the Terminal.

    First of all, I went to the project setting folder(the ".xcodeproj" actually is a folder).

    grep -i "Justis" *.*

    The above grep command result said the string "Justis" did exist in the file project.pbxproj!

    With nano, I saw the following in this file

    /* Begin PBXShellScriptBuildPhase section */
    3F3B364F0FD01DF6001754F2 /* ShellScript */ = {
    isa = PBXShellScriptBuildPhase;
    buildActionMask = 2147483647;
    files = (
    );
    inputPaths = (
    );
    outputPaths = (
    );
    runOnlyForDeploymentPostprocessing = 0;
    shellPath = /bin/sh;
    shellScript = "if [ \"${PLATFORM_NAME}\" == \"iphoneos\" ]; then\nplatform=/Developer/Platforms/iPhoneOS.platform\nallocate=${platform}/Developer/usr/bin/codesign_allocate\nexport CODESIGN_ALLOCATE=${allocate}\ncodesign -fs \"Justis Publishing Ltd\" \"${BUILT_PRODUCTS_DIR}/${WRAPPER_NAME}\"\nfi\n";
    };
    /* End PBXShellScriptBuildPhase section */


    I have no idea how and when I added this section to this project, but I think I don't need this section at all, so I deleted it and saved the file, then reopened Xcode, and rebuilt my project, Bingo! I got everything right!

    Like all other IDE, Xcode is not omnipotent. Sometime, you have to look into Makefile(here the project.pbxproj file), isn't it?