This document describes how to build and install uPortal 2.5.1 from source and link it to PostgresSQL 8.1.3 and deploy it on Tomcat 5.5.16 with JDK 1.5.0.
The first thing you need to do is download the uPortal source code. Download the uPortal-only package : get it here
Once you’ve got it, unpack it. I’ll assume you’ve unpacked it to /usr/local/src to get:
/usr/local/src/uPortal_rel-2-5-1
We’ll call this UP_HOME from now on.
Next you have to configure uPortal to work with postgres. For this, you’ll need the 8.1.3 JDBC driver : get it here
Download the 8.1 Build 405 driver and put the jar file, postgresql-8.1-405.jdbc3.jar in UP_HOME/lib
Now, edit UP_HOME/build.properties. My tomcat is in /usr/local/apache-tomcat-5.5.16 so I set this:
server.home=/usr/local/apache-tomcat-5.5.16
Locate the section that starts:
#==================== External Dependencies ===========================
comment out the current database driver:
#jdbcDriver.jar=${lib.path}/hsqldb.jar
and add the line:
jdbcDriver.jar=${lib.path}/postgresql-8.1-405.jdbc3.jar
Now open the file UP_HOME/properties/rdbm.properties and edit the postgres JDBC section:
##### PostgreSQL – example
jdbcDriver=org.postgresql.Driver
jdbcUrl=jdbc:postgresql://localhost:5432/uportal
jdbcUser=postgres
jdbcPassword=x
make sure you use your own database!
Now, before you can build from source, you have to add type mappings for postgres 8.1.3. Open the file UP_HOME/properties/db/dbloader.xml and add a type mapping for postgres 8.1.3:
<db-type-mapping>
<db-name>PostgreSQL</db-name>
<db-version>8.1.3</db-version>
<driver-name>PostgreSQL Native Driver</driver-name>
<driver-version>PostgreSQL 8.1 JDBC3 with SSL (build 405)</driver-version>
<type><generic>LONGVARCHAR</generic><local>TEXT</local></type>
<type><generic>VARCHAR</generic><local>VARCHAR</local></type>
<type><generic>LONGVARBINARY</generic><local>BYTEA</local></type>
<type><generic>VARBINARY</generic><local>BYTEA</local></type>
<type><generic>INTEGER</generic>< <local>integer</local></type>
</db-type-mapping>
If you don't add the type mapping exactly as above, for the driver you just downloaded, you'll get the database error:
Your database driver, 'PostgreSQL Native Driver', version 'PostgreSQL 8.1 JDBC3 with SSL (build 405)', was unable to find a local type name that matches the generic type name, 'LONGVARCHAR'.
Please add a mapped type for database 'PostgreSQL', version '8.1.3' inside 'file:/usr/local/src/uPortal_rel-2-5-1/build/WEB-INF/classes/properties/db/dbloader.xml' and run this program again.
If you're using a different version of postgres, make sure you match the driver version string from any error you get with the type mappings you add. Also, don't pay any attention to the file location - update the one in properties/db/dbloader.xml.
Now, create the uPortal database you'll use:
su postgres
createdb uportal
Now, you're ready to build. I built using JDK 1.5 as then you don't have to bother with the endorsed libraries. I also have JDK 1.4 installed so I have to specify which one to use at build time:
export JAVA_HOME=/System/Library/Frameworks/JavaVM.framework/Versions/1.5.0/Home
ant initportal
My Tomcat directory is writeable to my user but if your's isn't, you'll have to prefix the ant command with sudo.
This will build, initialise the database, install uPortal and deploy the portlets to /usr/local/apache-tomcat-5.5.16/webapps/uPortal. It also copies the configuration fragment:
/usr/local/apache-tomcat-5.5.16/conf/Catalina/localhost/uPortal.xml
However, before you can start it up, you have to fix a bug. uPortal doesn't work with Tomcat 5.5 due to JNDI Datasource configuration changes. In Tomcat 4.x/5.0.x this is used by uPortal in uPortal.xml:
<Resource name="jdbc/PortalDb" auth="Container" type="javax.sql.DataSource" />
<ResourceParams name="jdbc/PortalDb">
i.e. the Resource is named and then configured separately via a ResourceParams element. In Tomcat 5.5.x, this has changed and ResourceParams is no longer used. Instead, the configuration is specified in the Resource element. So you should replace the two Resource elements in uPortal.xml with the new format:
<Resource name="jdbc/PortalDb" auth="Container" type="javax.sql.DataSource" driverClassName="org.postgresql.Driver" url="jdbc:postgresql://localhost:5432/uportal" username="postgres" password="x" maxActive="20" maxIdle="10" maxWait="-1" />
<Resource name="jdbc/PersonDb" auth="Container" type="javax.sql.DataSource" driverClassName="org.postgresql.Driver" url="jdbc:postgresql://localhost:5432/uportal" username="postgres" password="x" maxActive="20" maxIdle="10" maxWait="-1" />
If you don't do this, you'll see this error in the logs:
Cannot create JDBC driver of class '' for connect URL 'null'
It took me ages to figure that one out.
You can forget about webapps/uPortal/META-INF/context.xml. Tomcat 5.5.x uses conf/Catalina/localhost/uPortal.xml to configure the datasources.
You can now start tomcat and access uPortal from:
http://localhost:8080/uPortal
References:
Tomcat 5.5.x JNDI Datasource HOW-TO
I’ve been playing around with Jetspeed to see if I can turn Bodington into a portal thingy. Well, turns out it’s possible and Bodington is now running as a portlet application under jetspeed.
It has a MyModules portlet associated with it. Although it’s called MyModules, the modules won’t work just now so it just displays the groups for a user – in a portlet. More about that in a mo.
You can display this portlet in uPortal via WSRP presumably. In effect, each portlet associated with bod will expose a chunk of bod functionality in whatever portal container supports WSRP.
It’s the same concept as the Guanxi IdP. Bod is wrapped in portlets as well now. Where bod was IdPed without touching a line of code, it’s now portalised without touching a line of code.
Now, for the interesting news. MyModules doesn’t work in a portlet as it has the concept of current user. Portlets don’t have that – they’re “remote” from the application although they can access the bod context.
It could be fixed by changing Minerva to accept a user id instead of finding it from the context. Then the portlet could call Minerva directly and get the modules for a specific user. i.e, LDAP uPortal and use the novell ID of the user to get their modules direct from the CLAN portlet.
Most of the stuff in bod uses the context to get the current user so bod really isn’t ready for portalisation but it can be done. It actually works!
There’s another gotcha. Most of the stuff in bod writes directly to the HttpServletResponse but portlets use RenderResponse so it’s not just a case of sharing responses. There has to be some sort of munging.
No doubt there’s a way round the issues but it should be possible to take each tool in turn and change how it initialises. Abstract it away from the bod context and User objects and all that and make it almost standalone, like a plugin. That allows portlets to access it and it in effect becomes a gateway for portlets into the bodington system.
Questionnaire tool springs to mind. Abstract it out a bit, give it a portlet and import into uPortal and consume via WSRP.
So, on that news, I’m off to read up on portals, portlets and other such exotica
Well, I’ve read some more and here’s the result:
Logging into CLAN to view your groups from within Jetspeed2 – click to enlarge
The above image shows two portlets within Jetspeed2 which are part of the Bodington portlet application. Each is linked to Bodington via the internal API. If you login in the top portlet, you’ll see your groups appear in the lower portlet. The authentication is handled by Bodington in the normal fashion, so if the underlying Bodington uses LDAP authentication, you use your LDAP credentials to login. After you authenticate, the login portlet communicates this to the groups portlet and it expands and displays the groups for the user.
I had to make one change to the Bodington source though. org.bodington.server.realm.LDAPAuthenticator. Normally, it relies on BuildingServlet.getBodingtonRoot() to find it’s ldap-authenticator.xml but when running as a portlet application, it doesn’t work and the LDAP module can’t config itself. The solution was to change it to load it’s config file from the CLASSPATH and put ldap-authenticator.xml in WEB-INF/classes.
Logged into CLAN and viewing your groups from within Jetspeed2 – click to enlarge
I’ve now got CLAN running under Jetspeed2 with inter-portlet communication. It doesn’t really do much at the moment apart from let you login and view your group memberships.
So, what can I do next?
Well, I added a profile portlet as well as portlet to display currently logged in users.
CLAN profile and logged in users portlets within Jetspeed2 – click to enlarge
The logged in users portlet is a completely new implementation of this Bodington functionality. It uses the PortletContext to store logged in users information with the login portlet adding and removing them when the login and logout.
Dump the database to text file, without BLOBs:
pg_dump -f backup.sql DATABASE_NAME
Restore the database from text file without BLOBs:
pgsql -d DATABASE_NAME -f backup.sql
Dump the database with BLOBs:
pg_dump -Ft -b DATABASE_NAME > backup.tar
Restore the database with BLOBs:
pg_restore -d DATABASE_NAME backup.tar
I saw it again, this time on a comment on the BBC page. That funny mix up between pressured and pressurised! It’s a hoot, I tell you:
“I didn’t want to do it but he pressurised me”
“I’m being pressurised into doing it”
“Pressurised”? Surely not. What, someone has stuck an airline up your bahookie and is pumping you up? Like a balloon? Nah! Really? puff puff puff…
Learn to speak – “pressured”! doh, I don’t know.
Next time you hear someone say this, just imagine them slowly inflating and flying off before your very eyes!
Python
First thing you need is Python : get it here
We’ll put it in /usr/local/python:
./configure –prefix=/usr/local/python
make
make install
The first you should do is make sure any previously installed Python interpreters are deleted. If you don’t, it’ll cause a lot of headache later on. There’s usually one at:
/usr/bin/python
so, do this to save your sanity:
cd /usr/bin
rm python
ln -s /usr/local/python/bin/python python
don’t forget to add /usr/local/python/bin to your PATH in /etc/profile, so that when you do:
which python
you’ll get:
/usr/local/python/bin/python
This is important to make sure Zope uses the python you just built and also that the LDAP lib you’re about to build uses it too.
openLDAP
A quick diversion here, as you’ll need to install openLDAP now, before building Python LDAP support. Get it here
Here’s how I normally configure openLDAP for an easy install:
export LIBS=-lresolv
./configure –prefix=/usr/local/openldap \
–enable-ldbm=no \
–enable-slapd=no \
–with-tls
then do:
make
make install
and that’s you got openLDAP installed.
LDAP support for Python
You now need python-ldap : get it here
edit it’s setup.cfg for a nice easy install:
library_dirs = /usr/local/openldap/lib
include_dirs = /usr/local/openldap/include
libs = ldap
then just do:
python setup.py build
python setup.py install
If you get errors such as these:
file Lib/ldap.py (for module ldap) not found
file Lib/ldap/schema.py (for module ldap.schema) not found
file Lib/ldap.py (for module ldap) not found
file Lib/ldap/schema.py (for module ldap.schema) not found
don’t worry about them as apparently they’re normal! Read it here
To test that the LDAP build worked, go into a shell and do:
python -c “import ldap,ldap.schema;print ldap.__version__”
You should get the version number displayed. If you get:
ImportError: No module named ldap
then you’ve most probably not got rid of the previously installed Python interpreter which lurks in /usr/bin
Zope
Zope now : get it here
Nice easy configure:
./configure –prefix=/usr/local/zope \
–with-python=/usr/local/python/bin/python
–with-python is important as it makes sure Zope uses the Python you’ve just build and not one of the lurkers on the system. If you get an error such as:
make: execvp: /usr/local/python: Permission denied
then you’ve done –with-python=/usr/local/python instead.
OK, off we go again:
make
make install
and we have Zope in /usr/local/zope. The next step is to go to /usr/local/zope and type:
bin/mkzopeinstance.py
to create a new instance. I just called mine “test” and gave it an admin username and password. This gave me an instance in:
/usr/local/zope/test
The next step is important. Edit:
/usr/local/zope/test/etc/zope.conf
and change effective-user to be the uid of a system user to run the instance as, instead of root. Then make /usr/local/zope/test and all it’s subdirs writeable to that user:
effective-user wwwrun
chown -R wwwrun test
You’re now ready to start your new Zope instance:
/usr/local/zope/test/bin/zopectl start
if you want to see any errors, which don’t get logged BTW, do:
/usr/local/zope/bin/zopectl fg
You should be able to go to:
http://yourzope.com:8080/manage
for the root instance and
http://yoursite.com:8080/test/manage
for your test instance, logging in as the user you specified when running mkzopeinstance.py
If all is well, shut Zope down, for now we install Plone:
/usr/local/zope/test/bin/zopectl stop
Plone
Plone is a Zope Product, get it here
What you must do is create a Products directory for it under your “test” instance:
mkdir /usr/local/zope/test/Products
if it doesn’t already exist. Then just decompress the Plone tarball and copy all those file into the Products directory:
cd Plone-2.1.2
cp -r * /usr/local/zope/test/Products
That’s it for now. Let’s add LDAP support to Plone now.
LDAP support for Plone
We now need LDAPUserFolder for Zope, get it here
All you have to do is decompress it and copy the directory to your test Products directory:
cp -r LDAPUserFolder /usr/local/zope/test/Products
and now interactively restart your Zope instance:
/usr/local/zope/test/bin/zopectl fg
to test for LDAP loading errors such as:
File “<string>”, line 1, in ?
ImportError: No module named ldap
if you see this then Zope is not using the Python you LDAP enabled. Go back to the Python section and make sure you’ve got rid of all lurkers and you’ve built and installed python-ldap. If you don’t see any errors, then shut it down again:
/usr/local/zope/test/bin/zopectl stop
and start it in daemon mode:
/usr/local/zope/test/bin/zopectl start
Install your new Plone by logging in to your Zope root instance:
http://yourzope.com:8080/manage
and adding a “Plone Site” from the “Add” droplist when in the root menu. You can then login to your Plone:
http://yourzope.com:8080/test/manage
You now have an LDAP enabled Zope and Plone. To configure Plone to use LDAP, follow the instuctions here. This page might help too.
This is how you publish to a webdav enabled website from Windows XP using My Network Places. If you’re out of the office you can set up a quick connection using Internet Explorer. I’ll explain that one later.
Publishing to your website from the desktop
- Go to Start->My Network Places
- Click on the text “Add a network place” on the left of the box
- You’ll now see a dialog box appear that displays the text “Welcome to the Add Network Place Wizard”. Click on the “Next” button at the bottom of the dialog box
- Make sure that “Choose another network location” is selected. If it isn’t, click on it. Click on the “Next” button
- In the box under the text “Internet or network address”, enter your webdav URL, e.g. http://mysite.com/publish
- Click on the “Next” button
- If the website is password protected, you’ll see a small dialog box appear. Enter your username and password and click the “OK” button
- If the dialog box appears again but your username is prefixed by the website URL, i.e. mysite.com/username it’s necessary to start again and enter a new webdav URL. Click on the “Cancel” button of the small dialog box
- Change your webdav URL to be of the form http://username@mysite.com/folder
- Click on the “Next” button
- The small dialog box will appear again if the website is password protected. Enter your username and password as before and click on the “OK” button
- A new box will appear now. Under the text “Type a name for this network place”, type a meaningful name for your website connection, e.g. “Publish to mysite.com”
- Click on the “Next” button
- A final box will appear telling you about your new connection. Click on the “Finish” button
- To publish to your website, all you have to do is open My Network Places (Start -> My Network Places) and double click on the name of your connection on the right of the screen. This will open your website. You can then just drag and drop files and folders from your PC to the website and vice versa
Publishing to your website from Internet Explorer
- Open Internet Explorer
- From the menu, choose File -> Open
- A dialog box will appear. Under the text “Type the internet address of a document or folder…”, type your webdav URL, e.g. http://mysite.com. Do NOT click on the “OK” button until you’ve read the next step
- Make sure the checkbox to the left of the text “Open as web folder” has a tick or a cross in it. If it doesn’t, click on the small blank square to the left of the “Open as web folder” text
- Click on the “OK” button now
- If the website is password protected, you’ll see a small dialog box appear. Enter your username and password and click the “OK” button
- If the dialog box appears again but your username is prefixed by the website URL, i.e. mysite.com/username it’s necessary to start again and enter a new webdav URL. Click on the “Cancel” button of the small dialog box
- Change your webdav URL to be of the form http://username@mysite.com/folder
- The small dialog box will appear again if the website is password protected. Enter your username and password as before and click on the “OK” button
- Your website will open and you can drap and drop files to it from your PC to Internet Explorer
In case you see a strange message such as “error 31 = ERROR_GEN_FAILURE” or similar, go to this Microsoft page