Wednesday, December 17, 2008

wix - It must use a registry key under HKCU as its KeyPath, not a file.

Took me a few minutes to figure out my problem with this error in wix: It must use a registry key under HKCU as its KeyPath, not a file.

My original code:
<Directory Id="AppDataFolderName="AppDataFolder">
  <Directory Id="MyAppFolderName="My">
    <Component Id="MyComponentGuid="cc509cb7-c1a1-46cf-8c62-7cbb0017783c">
      <File Id="test1.txtName="test1.txtKeyPath="yesSource="Files\test1.txt" />
    </Component>
  </Directory>
</Directory>

This is what it needed to be:
<Directory Id="AppDataFolderName="AppDataFolder">
  <Directory Id="MyAppFolderName="My">
    <Component Id="MyComponentGuid="cc509cb7-c1a1-46cf-8c62-7cbb0017783c">
    <RegistryKey Action="noneKey="myKeyNameRoot="HKCU>
         <RegistryValue Type="integerValue="1KeyPath="yes" />
    </RegistryKey>
      <File Id="test1.txtName="test1.txtKeyPath="yesSource="Files\test1.txt" />
    </Component>
  </Directory>
</Directory>

Monday, October 13, 2008

Good Technology Podcasts

Podcasts are an important part of developing as a developer.

Recently I have been listening to:

StackOverFlow
TWiT
Herding Code
SE Radio
.Net Rocks

There are a lot more good recomendations at this post:



Wednesday, September 17, 2008

Google Analytics Sucks!


Before I go on, I must say that I use Analytics every day, and it is by far the best tool I have found for monitoring site traffic.

The problem, though, is it does not let you get down to the nitty gritty details about a specific user. For example you could not find out what user, from what region, from what referring site, hit what content. You can find out all this information about groups of users, but not at the same time. I am guessing for privacy reasons (same reason you cannot obtain the IP). This becomes limiting quickly for me.



Maybe all this information is mute once you have hits in the thoasands per day, but when you are getting an average of one signup per day the individual user details are still very interesting and useful.

How to log the referring site

My web startup was deployed in June... It took me until this week to realize I should be recording the referring site for every signup. And no... Google Analytics is not a good solution for this.

The client side code goes something like this:
    <form>
Email
<input onfocus="javascript:document.getElementById('referringSite').value=document.referrer"
name="email" />
<!-- or with jquery: -->
<!-- <input onfocus="javascript:$('#referringSite').val(document.referrer);" name="email" />-->
Choose Password
<input type="password" name="password" value="" />
<input type="hidden" name="referringSite" value="" id="referringSite" />
<input name="submit" type="submit" value="Sign up!" />
</form>


So now, instead of knowing where I get the most hits from, I know where I get the most account creations from, which is what really matters.

Anyone know of any other super valuable info to record?

Friday, August 22, 2008

Clipboard caching utilities

Over the past year or so, I have become dependent upon clipboard caching utilities. These are programs that run in the background that keep track of EVERYTHING copied (ctr-c). I wonder why this functionality is not built into any mainstream operating system. Maybe because Clippy ("one of the worst software design blunders in the annals of computing" -Smithsonian Magazine) was our first taste of clipboard caching.

I have been using CLCL which has been working fairly well for me. I have its cache limit set at 100 copies, which goes back a few days (which is suprising for how much I copy!).

But lately my copy function will randomly stop working until I restart. Which brings up two questions I have.
  1. Does anyone know if this is related to CLCL?
  2. If so, does the restarting every couple days diminish the productivity gained via the utility?
Anyone have any thoughts? What other utilities do you use?

Monday, August 4, 2008

XSLT example template that returns boolean

In XSLT you can create templates that act as boolean functions.

<xsl:template match="/">
<!-- create variable named cat to store boolean value -->
<xsl:variable name="cat">
<xsl:call-template name="HasCat"/>
</xsl:variable>

<xsl:when test="$cat= 'true'" >
<!-- do something because it has a child element named cat -->
</xsl:when>
</xsl:template>


<xsl:template name="HasCat">
<xsl:choose>
<xsl:when test="count(descendant-or-self::*[contains(local-name(), 'Cat')]) > 0">
<xsl:value-of select="true()"/>
</xsl:when>
<xsl:otherwise>
<xsl:value-of select="false()"/>
</xsl:otherwise>
</xsl:choose>
</xsl:template>

Monday, July 14, 2008

What is fully-qualified class name

When people use the term fully-qualified class name in the Java world, they mean the class name with its package name prepended.

For example if I had the class HelloWorld:

Class: HelloWorld
Package: com.blogger.nofoe
Fully-qualified name: com.blogger.nofoe.HelloWorld



Note: The naming convention for packages in java goes {domain extension}.{domain name}.{project name}

java main print out args - snippet

Code to print out all arguments being passed to the main method:

    public static void main(String[] args) {

//print out arguments
for (int i = 0; i < args.length; i++) {
System.out.print("args["+i+"]: " + args[i] + "\n");

}
}

Monday, June 23, 2008

How to set a document to its next major version using DFC

The code below overrides DfDocument.doCheckin in my TBO (Type Based Object). The method sets the document to its next major version when it is promoted to lifecycle state Final.

protected void doPromote(String state, boolean override, boolean fTestOnly, Object[] extArgs ) throws DfException {

super.doPromote(state, override, fTestOnly, extArgs);


if (this.getCurrentStateName().equals("Final")){
if(this.isCheckedOut() == true){
throw new DfException("Cannot version if object is checked out.");
}

String newMajorVersion = this.getVersionPolicy().getNextMajorLabel();
this.mark(newMajorVersion);
this.save();
}
}
If the code above is not flexible enough... Below is the example from Documentum that uses operations to set the document to the next major version by overriding DfDocument.doCheckin.

public static void doCheckin( String strPath, IDfSession session ) throws DfException {
IDfClientX clientx = new DfClientX();
IDfCheckinOperation operation = clientx.getCheckinOperation();

IDfSysObject sysObj = (IDfSysObject) session.getObjectByPath( strPath );
if( sysObj == null ) {
System.out.println("Object " + strPath + " can not be found.");
return;
}

if (sysObj.isCheckedOut() == false) {
System.out.println("Object " + strPath + " is not checked out.");
return;
}

IDfCheckinNode node;
if( sysObj.isVirtualDocument() ) {
IDfVirtualDocument vDoc = sysObj.asVirtualDocument( "CURRENT", false );
node = (IDfCheckinNode)operation.add(vDoc);
} else {
node = (IDfCheckinNode)operation.add(sysObj);
}

//Other options for setCheckinVersion: VERSION_NOT_SET, NEXT_MAJOR,
// NEXT_MINOR, BRANCH_VERSION
operation.setCheckinVersion(IDfCheckinOperation.NEXT_MAJOR);
operation.execute();

}

Tuesday, June 17, 2008

Java 1.4 get node text

The Java JRE 1.4 is missing the method org.w3c.dom.Node.getTextContent().

java.lang.NoSuchMethodError: org.w3c.dom.Node.getTextContent()

This is unfortunate, but you DO NOT have to upgrade to Java JRE 1.5! Use the function below as a replacement for getTextContent().


    /**
* Recursive implementation of the method
* org.w3c.dom.Node.getTextContent which is present in JDK 1.5 but not 1.4
* @author Tobias Hinnerup
* @param node Node that you need to get the text content of
* @return
*/

private static String getTextContent(Node node) {
Node child;
String sContent = node.getNodeValue() != null ? node.getNodeValue() : "";

NodeList nodes = node.getChildNodes();
for(int i = 0; i < nodes.getLength(); i++) {
child = nodes.item(i);
sContent += child.getNodeValue() != null ? child.getNodeValue() : "";
if(nodes.item(i).getChildNodes().getLength() > 0) {
sContent += getTextContent(nodes.item(i));
}
}

return sContent;
}

Tuesday, June 3, 2008

How to store an array in a Java properties file

Below describes how to store a two-dimensional array in a properties file.

Delineate the items in the array by commas and semicolons.

The properties file would be like:


myProperty=name1,age1,job1,location1;name2,age2,job2,location2;

So each person is divided by a semicolin, but the attribute of that person by a comma. The same code works with any amount of attributes per person.

Split up the property into a String[][] variable type:
    //get array split up by the semicolin
String[] a = propFile.getProperty(propertyName).split(";");

//create the two dimensional array with correct size
String[][] array = new String[a.length][a.length];

//combine the arrays split by semicolin and comma
for(int i = 0;i < a.length;i++) {
array[i] = a[i].split(",");
}

Now you have a two dimensional array from a property file!

Below is a complete example:


Properties File
#delineated by Name,Capital,Nickname;Name,Capital,Nickname; etc....
stateInfo=California,Sacramento,The Golden State;Pennsylvania,Philadelphia,Keystone State;Texas,Austin,Lone Star State

Java Code
package myProject;

import java.io.FileInputStream;
import java.util.Properties;

public class Main {

//Key for 2nd part of array
final static int NAME = 0;
final static int CAPITAL = 1;
final static int NICKNAME = 2;

public static void main(String[] args) throws Exception {

//get properties file
Properties prop = new Properties();
prop.load(new FileInputStream("C:\\myStatesPropertiesFile.txt"));

//get two dimensional array from the properties file that has been delineated
String[][] stateInfos = fetchArrayFromPropFile("stateInfo",prop);


//below code will print out all the states, their capitals, and nicknames
for (int i = 0; i < stateInfos.length; i++) {
System.out.print("State "+ i + ":");
System.out.print("\n");
System.out.print("Name: " + stateInfos[i][NAME]);
System.out.print("\n");
System.out.print("Capital: " + stateInfos[i][CAPITAL]);
System.out.print("\n");
System.out.print("NickName: " + stateInfos[i][NICKNAME]);
System.out.print("\n");

}
}

/**
* Creates two dimensional array from delineated string in properties file
* @param propertyName name of the property as in the file
* @param propFile the instance of the Properties file that has the property
* @return two dimensional array
*/

private static String[][] fetchArrayFromPropFile(String propertyName, Properties propFile) {

//get array split up by the semicolin
String[] a = propFile.getProperty(propertyName).split(";");

//create the two dimensional array with correct size
String[][] array = new String[a.length][a.length];

//combine the arrays split by semicolin and comma
for(int i = 0;i < a.length;i++) {
array[i] = a[i].split(",");
}
return array;
}
}

Thursday, May 22, 2008

How to Insert HTML into a Webtop component using a label

Below I will show you how to output plain text or HTML to your custom component. Thats right! You can output HTML to the component screen from the class using the Label tag!
Documentum outputs dynamic text and controls to Webtop Components via custom JSP tags.

Example outputting plain text to the component screen

JSP file:
<dmf:label name="documentumMessage"  />
Class file:
Label msg1 = (Label) getControl("documentumMessage",Label.class);
msg1.setLabel("documentum is crazy");


Example outputting html to the component screen:

JSP file:
<dmf:label name="documentumMessageWithHtml" encodelabel="false"/>
Class file:
Label msg2 = (Label) getControl("documentumMessageWithHtml",Label.class);
msg2.setLabel("<strong>documentum is <em>crazy</em></strong><br />");

If you do not set encodelabel="false", the HTML will be printed to the screen instead of rendered. (Do not try and set this attribute from the Class file because it will not work.)


Output

Friday, May 16, 2008

How to view the difference between two files

I found an easy way to view the dif between the text of two files. Originally the only way I knew of was to load them into subversion. Then I realized Notepad++ (the best text editor I have found by far!) has a built inplugin called Compare which highlights the differences like subversion does.

Check out this screen shot

Wednesday, May 14, 2008

Dell Inspiron Desktop 530 no sound

My roomate just received a Dell Inspiron 530 and the sound did not work, and flash videos would freeze.

To fix this download the Realtek ALC888 HD Audio drivers from Dell. This should fix the sound problem and the video problem.

Reason: The 530's were designed to run Vista. Do to high demand for XP they started loading XP onto them, but not installing the proper drivers. For some reason this fixed the flash video freezing as well.

How to export a Virtual Document in Documentum.

First you will need to convert the IDfSysObject to an IDfVirtualDocument.

        //verify the object is a virtual document
//the variable doc is the IDfSysObject that you are working with
if (doc.isVirtualDocument()) {
IDfVirtualDocument v = doc.asVirtualDocument("CURRENT",false);
exportVirtualDocument(v, exportDir, "");
} else {
throw new DfException("Must be a virtual document to export.");
}


Then take the doc variable and call this method:

    /**
* Exports virtual document to the destination directory
*
* @param doc virtual document to be exported
* @param destDir directory virtual document should be exported to
* @param exportFormat export format (such as html, or you can use the da to create a new one)
* @throws Exception
*/

private void exportVirtualDocument(IDfVirtualDocument doc,
String destDir, String exportFormat) throws Exception {
IDfClientX clientx = new DfClientX();

IDfExportOperation operation = clientx.getExportOperation();
operation.setDestinationDirectory(destDir);
IDfExportNode node = (IDfExportNode) operation.add(doc);
node.setFormat(exportFormat);

// Execute the operation
boolean executeFlag = operation.execute();

// Check if any errors occured during the execution of the operation
if (executeFlag == false) {
// Get the list of errors
IDfList errorList = operation.getErrors();
String message = "";
IDfOperationError error = null;

// Iterate through the errors and concatenate the error messages
for (int i = 0; i < errorList.getCount(); i++) {
error = (IDfOperationError) errorList.get(i);
message += error.getMessage();
}

if (message.length() > 0) {
// Create a DfException to report the errors
DfException e = new DfException();
e.setMessage(message);
throw e;
}
}
}

How to create a new page in Webtop - Documentum

New to Documentum or Webtop and trying to create a custom page for getting input or changing settings or sending an item to a queue?

Want to get to the page using that dropdown menu Webtop has?

Important terminology.
  • A page in Webtop is called a Component
  • The dropdown menu above the objects is called the Menubar
This is all part of the documentum WDK (Web Development Kit). I recommend downloading the JavaDoc from EMC Developer Network. You will need to sign up but it is free and there is lots of good Documentum related stuff on there.

Anyway on to creating your Webtop Component. This document will guide you through the creation.
Read this document on Scribd: HelloWorldWDKComponent


Tips:
If you want to do some actions when the Ok or Cancel buttons are pressed in the component.... Here is the code for the webtop OK button and Cancel button events:

    public boolean onCommitChanges() {
//this method is called when the user clicks the OK button
}

public boolean onCancelChanges() {
//this method is called when the user clicks the cancel button
}
And remember to download the WDK API javadoc. This zip also contains the difference between WDK version 5.3 and 6.

Post a comment or email me if you have any questions.






Read this doc on Scribd: HelloWorldWDKComponent