Monday, April 13, 2009

Creating K2 Environment Fields with Environment Library API

I know that you can use a deployment package to move environment settings to different servers, but I wanted to see if I can create them programmatically. The process of creating Environment Fields can be a time consuming and tedious task, especially if you have a large number of fields. Typically in a real-world project, a list of Fields are already defined in a functional document somewhere, so to have a utility which can create fields from a list in a text file for example could be a big time saver. At the time of this writing, documentation on how to do this kind of thing was rather scarce, hence this post ;-)

The trick is to get a new instance of an Environment Field since is doesn’t have a new() constructor, you have to get a new instance by using the CreateFieldInstance() method of the EnvironmentFieldType class.

Steps:

  1. Create a new EnvironmentSettingsManager Instance and Connect to the K2 Server using the ConnectToServer() method of the EnvironmentSettingsManager instance.
  2. Create a new EnvironmentTemplateCollection Instance and a new EnvironmentInstanceCollection Instance.
  3. Select the Environment Template to use (e.g. Default Template) and select the Environment to use (e.g. Development)
  4. Get a handle on the EnvironmentFieldType you want to use by calling the EnvironmentSettingsManager.EnvironmentFieldTypes.GetItemByFriendlyName("Miscellaneous Field")
  5. Get a new EnvironmentField instance by calling CreateFieldInstance() method of the EnvironmentFieldType instance.
  6. Set the properties of the EnvironmentField instance
  7. Add the Field to the EnvironmentFieldCollection of the Environment Instance with the Add(newField) method of the EnvironmentFieldCollection
  8. Call the SaveUpdate() method of the EnvironmentField

Code:

EnvironmentInstance ei = new EnvironmentInstance();
ei = eic.GetItemByName("Development");
esm.ChangeEnvironment(ei.EnvironmentId);
EnvironmentFieldType eft = esm.EnvironmentFieldTypes.GetItemByFriendlyName("Miscellaneous Field");
EnvironmentField ef = (EnvironmentField)eft.CreateFieldInstance();
ef.FieldName = "DeonTestField";
ef.FieldDescription = "Deon Test Field";
ef.DisplayName = "DeonTestField";
ef.Value = "Some Value in Here";
efc = new EnvironmentFieldCollection(ei);
efc = ei.EnvironmentFields;
efc.Add(ef);
ef.SaveUpdate();

Friday, October 03, 2008

K2 BlackPearl 807

The 807 version of BlackPearl was released on the 24th of September and so far I am pretty impressed. The Workspace imageManagement console features a new section called User Managers where you can configure your additional AD Domains. 

 

The long awaited Out-Of-Office features are also in 807, and it's great!! Some highlights:

  • A user can configure multiple users as recipients of his worklist items when he's out of office
  • He can create Exception Rules, to send Worklist items for specific activities to different users while out-of-office
  • An administrator can create and edit out-of-office rules for users
  • Existing worklist items are immediately delegated to the designated users when out-of-office is tuned on.

image

Note: If you are using the Workflow Client API to action worklist items, you have to take additional steps to handle out-of-office functionality, specifically you have to check for the presence of the SharedUser Query string an addition to the Serial Number (SN) Query String, following is some sample code:

private void openMyTask()
{
        string sn = Request.QueryString["SN"];
        if (sn != null && sn != "")
        {
            Connection k2Conn = new Connection();
            WorklistItem wli;
            try
            {
                k2Conn.Open(ConfigurationManager.AppSettings["k2Connection"]);
                wli = getWLI(k2Conn, sn, Request.QueryString["SharedUser"], Request.QueryString["ManagedUser"]);
                //get Data Fields
                //get Actions
                //etc.
            }
            catch (Exception ex)
            {
                //Handle Exception
            }
            finally
            {
                k2Conn.Close();
            }
        }
        else
        {
            //No Serial Number - show Error
        }
}

private WorklistItem getWLI(Connection conn, string serialNumber, string sharedUser,string managedUser)
{
       WorklistItem worklistItem = null;
       // normal user
       if ((sharedUser == null) && (managedUser == null))
       {
            worklistItem = conn.OpenWorklistItem(serialNumber, "ASP");
       }
       // Out of Office user
       if ((sharedUser != null) && (managedUser == null))
       {
             worklistItem = conn.OpenSharedWorklistItem(sharedUser, managedUser, serialNumber);
       }
       // normal Manager
       if ((sharedUser == null) && (managedUser != null))
       {
             worklistItem = conn.OpenManagedWorklistItem(managedUser, serialNumber);
       }
       // Out of Office Manager
       if ((sharedUser != null) && (managedUser != null))
       {
          worklistItem = conn.OpenSharedWorklistItem(sharedUser, managedUser, serialNumber);
       }
       return worklistItem;           
    }
}

Technorati Tags:

Friday, July 11, 2008

New Dev Environment

It is finally up and running!
My Dell E1505 with 2 GB RAM was just not cutting it anymore, it worked fine for K2.net 2003 Dev but the resource requirements for K2 [blackpearl] has grown substantially. Even if I upgrade to a super notebook with 4 GB RAM, I still would be limited in what I want out of a proper Dev environment. I wanted to have an environment which closely matches real-world K2 production environments, and trying to build that with decent performance on a Notebook with 4 GB RAM is close to impossible.

So, I decided to move my DEV environment from my notebook onto a virtualization server. Now I have 5 virtual servers and a virtual workstation as my new DEV environment. It is a true multi-domain distributed K2 environment. The beauty is that I was able to build a fairly powerful Virtual Host Server for about the same price as a high-end 4 GB Notebook, i.e. for about $2000. Here is what 2000 bucks got me:

Rack Server from serversdirect.com (http://www.serversdirect.com)

· Motherboard: Supermicro X7DVL-I Server Board
· CPU #1: Intel Quad-Core Xeon E5405 Processor @ 2.00GHz
· CPU #2: Intel Quad-Core Xeon E5405 Processor @ 2.00GHz
· Memory: 10 GB , ECC Fully Buffered
· Disk I/O: 6x SATA2 3.0Gbps Ports via
· H/Disk #1: Seagate SATAII 160GB
· H/Disk #2: Maxtor SATAII 1TB
· Network: Integrated Intel Dual-Port Gigabit Ethernet Controller

And, this is what it looks like:

image

Thursday, July 10, 2008

Multi-Domain blues update 2

Turns out there is a small problem with K2 caching of AD users in a multi-domain environment. A fix should be included in the next release of blackpearl. The work-around in the interim is to turn off caching by:

Changing the 'ADCache' value in the RoleInit column of the security label to 0 (the default is 10).
For example:
"<roleprovider><init>ADCache=0;LDAPPath=LDAP://DC=K2DEMO,DC=LOCAL;..."
This will force K2 to always query AD rather than using the cache.

Technorati Tags:

Thursday, July 03, 2008

K2 Kerberos Troubleshooting

I recently had a hard time troubleshooting a Kerberos issue at a client. The Kerberos goodies (SPN's, Delegation etc) were created by the SysAdmin team based on instructions from me but unfortunately I was not present when they did so I had to verify the Kerberos setup after everything was created. The symptoms was the usual, APP Pool service account auth to K2 server using NTLM and naturally the user credentials aren't delegated, resulting in Anonymous connection to K2 server. Everything checked out: SPN's on K2 Server Service Account, SPN's on APP Pool Account, constrained delegation from APP Pool to K2 Server configured etc. After much head scratching I discovered a DUPLICATE set of SPN's on the K2 Services which caused Kerberos to break. A Service can only run as one account, so to create another set of SPN's for the SAME Services on another account is a no-no. The following would be a problem (not showing FQN SPN's):
ServiceAccount1 SPN's:
K2Server/SERVERA:5252
K2HostServer/SERVERA:5555
ServiceAccount2 SPN's:
K2Server/SERVERA:5252
K2HostServer/SERVERA:5555
Delete the SPN's for ServiceAccount2 and you're good to go.

Technorati Tags:

Friday, June 20, 2008

PDF Output from K2 with InfoPath Signed Form

The solution required that the K2 workflow convert the final signed InfoPath Form into a PDF document, and save that to a SharePoint Library. This was an interesting one. Since all the InfoPath XML is stored in K2 Datafields, just creating a new PDF from the K2 XML datafields would be 'invalid' since it would represent something that was not signed by the final approver, right?

I discovered (thanks Jason for the tip-off) that InfoPath actually stores a snap-shot picture (PNG format) of the form state that was signed inside the xml as a base64 encoded string. So, the task turned into extracting the base64 encoded string representing the image, load it into an image object and create a PDF with the picture in it.

The challenge was that the details of the signature node is not part of the schema, so you can't just load the signature xml node into the DOM and navigate to the picture node, nope. So I used good old string manipulation to get to the picture string. I then loaded the picture string into a memory stream, created an image from that and used iTextCSharp to create a

PDF with the image in it. Pretty neat. Below is my sample K2 InfoPath process:

image 

Sunday, June 15, 2008

Multi-Domain blues update

K2 Support suggested a work-around to solve the problem in the mean time, it involves modifying the SecurityLabels table in the HostServer database. Those who have deployed K2 in a multi-domain environment, knows about this kb article:http://kb.k2workflow.com/articles/kb000182.aspx 
In our case K2 is not installed in the Parent domain but in one of two child domains, so my <init> tag pointed to the domain in which K2 was installed, this seems to have caused the problem. I modified the <init> tag to point to the parent domain and the problem appears to be resolved.

Geeky outdated cheap servers

Unfortunately, the saying "you get what you pay for" has been proved correct, at my expense that is. Here's the story:
With K2 [blackpearl], the demand on system resources (CPU, Memory) has almost grown beyond belief. I have seen Visual Studio easily consume over 1GB of RAM while working with K2 [blackpearl] studio. The CPU is also not spared, during development, deployment and running of processes, the CPU constantly hits 100% utilization. Al lot of this has to do with the fact that a single server VPC with 1.2GB of RAM is just not cutting it anymore. My humble Dell E105 is limited to 2GB RAM max, so I have a problem.
Notebooks typically come with a max of 4GB of ram and, they are expensive. I was looking for getting the most bang for the buck, so I decided to buy a server which will be capable of running multiple VM's as apposed to a more powerful notebook. A tip-off, lead me to investigate a lucrative deal from a geek shop in Oceanside, CA. A dual Xeon CPU rack server with 1GB RAM with $300 bucks, I went for it. I did not really get what I wanted. Turns out the motherboard is a 2003 board which has been discontinued, same goes for the 2.4 GHz Xeon CPU's. Unlike the later Xeon's, these ancient ones are still 32-bit, which immediately put a dent in my 16GB super server plan since countless problems exist when a 32-bit OS tries to address memory above 3GB. I ordered some extra RAM the same day I bought the server. As soon as the RAM arrived I started putting the server together, but there was a problem. No matter what I tried, windows wouldn't start or even run the setup with more than 3GB of RAM installed. Countless hours were wasted getting the damn thing to work with more than 3GB of RAM. Even with memory from two different suppliers, MEMTEST 86+ would throw out 1000's of errors with more than 3GB installed. I finally gave up and took the server back. image
I now ordered a more up-to-date rack server (left) for $1500. The m/board was released in 2008 and it takes 2 Quad-Core Xeon E5420 Processors. And yes, they are 64-bit processors. It's going to be a mission to get the memory swapped at the supplier, but I can't wait for this baby to arrive.