Plone
2010-08-22
Migrating content (folders) from Plone 3 to Plone 4 via zexp import
I had a need (and a problem) moving some content from a Zope 2.10/ Plone 3.3 instance to a Zope 2.12/Plone 4 instance. The path I have chosen was that of the least resistence, which for me was exporting the folder I was interested as a zexp file from the old instance and importing it in the new Plone instance. According to some members of the #plone IRC channel, this method of getting content from one zope instance to another is not possible, or at least not supported. I supposed that's correct, zexp import works best for moving content between identical zope instances, but, as they say, necessity is the mother of learning.
The issue is that the implementation of folders has changed from Plone 3 to 4 to use BTrees, which greatly improves performance. The problem is that, when viewing imported folders, I got the following traceback:
Traceback (innermost last):
* Module ZPublisher.Publish, line 116, in publish
* Module ZPublisher.BaseRequest, line 434, in traverse
* Module Products.CMFCore.DynamicType, line 150, in __before_publishing_traverse__
* Module Products.CMFDynamicViewFTI.fti, line 215, in queryMethodID
* Module Products.CMFDynamicViewFTI.fti, line 182, in defaultView
* Module Products.CMFPlone.PloneTool, line 840, in browserDefault
* Module Products.CMFPlone.PloneTool, line 708, in getDefaultPage
* Module Products.CMFPlone.utils, line 81, in getDefaultPage
* Module plone.app.layout.navigation.defaultpage, line 32, in getDefaultPage
* Module plone.app.layout.navigation.defaultpage, line 75, in getDefaultPage
* Module Products.BTreeFolder2.BTreeFolder2, line 337, in has_key
AttributeError: 'NoneType' object has no attribute 'has_key'
The solution was to call @@migrate-btrees on the imported folder, which fixes that folder and makes it conform to the latest implementation.
One final note, the default Plone buildout doesn't have a folder called "import" anywhere in the buildout, so one needs to be created inside the "client home folder", which is the folder of your plone and buildout instance, the one that hosts the bin, parts and var folders.
2010-02-24
Generating products outside of the Products.* namespace with ArchGenXML
I'm a die hard in regards to ArchGenXML usage. The number of things to know about when creating new content types for Plone is just too high. Package structure, Zope package registration, content types registration, QuickInstaller registration, GenericSetup profiles, skins registration, workflows, etc. I can go in and do changes to the code, and add to it, but generating it from scratch is a gigantic task, especially for my use case, where I need to start a new project with about 7 content types.
Now to the problem: ArchGenXML assumes (and hardcodes in its templates) the Products.* prefix for your package. I don't have any problems with it, but my employer uses a different package structure so for uniformity I need to follow their standards. 15 minutes of poking and changing through agx enabled me to change it so it would generate GS xml files with the proper namespace (based on a new model level TGV named "namespace" that I have created). After assessing the difficulty of the task and being under time pressure, I've decided to go the dumb route, which I'm documenting below:
My generation script is something like this:
./archgenxml -c archgenxml.cfg myproduct.zuml #rename Products.myproduct to ns.myproduct find myproduct/* -type f -print | xargs sed -i 's/Products\.myproduct/ns\.myproduct/g' #in the xml type profiles, replace myproduct by ns.myproduct find myproduct/* -type f -print | xargs sed -i 's/>myproduct</>ns\.myproduct</g' #in the profiles.zcml, rename the profile to ns.myproduct find myproduct/* -type f -print | xargs sed -i 's/title=\"myproduct\"/title=\"ns\.myproduct\"/g'
Notice the sed lines, which change the source code to point to "ns.myproduct" instead of "Products.myproduct". Now there's just two more problems, which are actually AGX bugs:
- the FilesystemDirectoryViews registered for the skin are incorect, so you'll need to insert this in ns/myproduct/__init__.py
from Products.CMFCore import utils
from Globals import package_home
from os.path import dirname
ppath = utils.ProductsPath
utils.ProductsPath.append(dirname(package_home(product_globals)))
DirectoryView.registerDirectory('skins', product_globals)
utils.ProductsPath = ppath
- trying to get AGX to output the code inside a two level deep folder doesn't work (it crashes), so you'll need to move this script file and the model just above the "myproduct" folder, inside the "ns" namespace.
That's about it. Hopefully I'll find the time to fix the two bugs and add the namespace improvement in the next week. Still need to do the review for Plone for Education, which I have received for free from the publisher.
2009-04-16
The sorry state of internationalization in Plone
Ever since Plone 2.5 stopped being the hot new thing in the Plone world, the state of content internationalization support in Plone has been declining. Partly due to the difficulty of extending Zope 2 products, LinguaPlone has always been a hack, but at least back then it worked. These days I'm not heavily involved with Plone, but whenever I need to add LinguaPlone to a Plone 3 site, I cringe and weep, especially that those projects never allocate time for me to fix the obvious problems. Some of those problems, in current Plone 3.3 rc2 are:
- the flags are no longer grayed to indicate that a certain translation is unavailable
- the switchLanguage script doesn't work anymore, it won't redirect you to the translated content; the LanguageTool is broken (won't take VHM into consideration) and an update was released, but the versions.cfg file on plone.org hasn't been updated yet, so you need to add a [versions] section, with the correct specification for the Products.PloneLanguageTool
- the changeLanguage script was removed, in favor of doing a direct translation. Wops, now it's possible to translate into neutral, which gets you fast into an ugly traceback that you won't be able to get rid of.
- the language neutral behaviour for fields is broken. Example: I have a content type with the neutral fields, when translating a content item the content of those fields is erased. This is something that I'll have to fix.
On the upside, the translation management mechanism (after some hickups) has improved.
I don't have access to the Plone subversion. I already had some discussions with two of the developers that have done the latest changes to LP, but they either didn't understand the problems or didn't have time to do the fixes themselves. To make it easier for myself and stimulate my interest in the LP development, I have copied the latest LP trunk to Collective, in a location called Products.LinguaPlone-Unofficial. This version also has a check for the case when there's a translation into Neutral, so it should fix the error detailed above.
Update:
Another problems solved: I've wanted to be able to switch languages based on the subdomain (ro.site.com, en.site.com), which should be supported by the PloneLanguageTool, but didn't work for me. Digging down, I found the problem: plone.i18n.locales.cctld has a list that associates TLDs to languages, but most of the TLDs don't have a language associated to them! This issue should be at least highlighted in the documentation for PloneLanguageTool.
One more weird problem, which caused me to blame LP for even more problems than it has at fault: upgrading as site from Plone 3.2 to 3.3 rc2 broke the LP language selector, by making the default Plone one override the LP one (where it should be the other way). I was able to solve the problem by customizing the template for the LP language selector (with no change)
2009-02-15
Using mechanize to process protected Plone pages
One of my long-running projects involves a workflow where content is produced in a Plone site, with the data later extracted and processed in various ways (including scripting Scribus to layout this data in a book). Initially the site where the content was produced wasn't protected, so I could run a simple urllib script to download the content and process it using lxml. A recent change in the workflow security settings meant this script didn't work anymore and I had to remember how to login into a Plone site using urllib2. Some google searches found me nothing, but I remembered that the zope.testbrowser can be easily used to run a programatical browsing session, complete with cookies support. But trying to install zope.testbrowser standalone in a buildout didn't lend to too much success, due to some dependency problems (and even after I covered for those dependencies, it still broke somewhere in zope.app.testing).
The solution was to use just the mechanize package, on top of which zope.testbrowser is built. mechanize has a slightly different API (more modern) and doesn't do so much handholding as zope.testbrowser, but I only need to process one form. In the end my script looks something like this (the asxmllist page is just an xml page that returns a list of urls to the entities that I want to process):
import lxml.etree
import os
import os.path
import urllib
import mechanize
loginurl = "http://example.com/login_form"
listurl = "http://example.com/asxmllist"
def run():
curdir = os.getcwd()
datadir = os.path.join(curdir, 'data')
if not os.path.exists(datadir):
os.makedirs(datadir)
b = mechanize.Browser()
b.open(loginurl)
b.select_form(nr=1)
b['__ac_name'] = "username"
b['__ac_password'] = "password"
b.submit()
b.open(listurl)
etree = lxml.etree.parse(b.response())
for entry in etree.xpath('//entry'):
url = entry.get('url')
print "Processing " + url
e = lxml.etree.parse(b.open(url + '/asxml'))
id = e.find('id').text
print "Got entry " + id
fpath = os.path.join(datadir, id + '.xml')
f = open(fpath, 'w')
xml = lxml.etree.tostring(e)
f.write(xml)
f.close()
print "Saved " + fpath
if __name__ == "__main__":
run()
2009-02-11
Variable keys in dictionaries with Page Templates TALES syntax
I admit, I didn't knew this until now. In the following construction:
<div tal:content="somedict/keyname/someattr" />
"keyname" is taken as a string, it's the literal name of the key for the somedict mapping. To use a variable instead of the literal value of the key name, I used to do:
<div tal:content="python somedict[key].someattr" />
Browsing through the zope.app.catalog code, I saw that there's actually a way to use the TALES syntax:
<div tal:content="somedict/?key/someattr" />
I'm not sure that this works with TTW code in Zope 2 (I expect that it works with browser views), so I'll just have to try this next time I have the chance.
2009-01-06
A list of Javascript files loaded by Plone 2.5
A simple deployment of a Plone 2.5 site (I know, antiquated) means that the pages shown for anonymous users are loaded with JS and CSS content that they will not need. They are, usually, the biggest group of visitors, so it is important do make the pages load fast, to have a good impression for first time visitors. The introduction of the Resource Registry in Plone 2.5 makes it easy to set the order and the conditions to load each resource (and, as a result, the merging conditions between resource files), but there's no page to document what each JS file does, for example (AFAIK). Because of my recent need to optimize such a site, I've created a list of the javascript files loaded by Plone 2.5. Plone 3.x makes it even easier to make sure that you get the minimum number of merged resource files by having the "Automatic grouping" function, but for Plone 2.5 I had to rearange the files myself to get the best result (3 JS files: one for anonymous users, one for users that are authenticated and one that is loaded for Kupu).
Crossroads: a very good load balancing solution
Recently Martin Aspeli published a very nice buildout recipe that implements a complete setup for a production Zope/Plone server. One of the key components in that setup is the load balancer, which is implemented using the load balancer capabilities of nginx. Nginx might be a good load balancer, but it has a problem with the way Zope/Plone works: the first page loads, for a newly restarted Plone instance are very slow (especially if the site or the catalogs are big). It would be nice to have a way of telling nginx to take out one of the Zope instances from the cluster and then add it back once it's restarted and has its caches warmed. Sure, you could probably script something that would change the buildout options and reload nginx, but why bother when there's a load balancer that offers this and much more?
Crossroads (in its second version, at the moment 2.41) might lack the popularity when compared to perlball, pound or haproxy and may not even have the same features or performances (it's good enough for my needs and I haven't cross-benchmarked), but it's fast, easy to configure and, best of all, it can be configured to provide a web configuration/administration interface. This way, when a Zope server needs to be updated, I can take out the ZEO client from the balancer, restart it in supervisor, warm up the caches by calling the zope sites directly and then add it back to the cluster. The only faults that I could find to it is that the compilation mechanism is not very well tested (I couldn't complete an install with a specific destination prefix. Just checkout the Crossroads trunk or a tag and do a "make local", then you can use the xr binary from that folder). On the other hand, it's pretty well featured: it has sticky sessions, HTTP awarness (although its documentation recommends treating the http servers with the TCP algorithm), can use an external program to determine backend states (and could be plugged this way with Zope's ICP support), etc.
Below is a screenshot of the Crossroads administration interface, with Crossroads started with the following script:
#!/bin/sh XR=/usr/sbin/xr SERVER="-s http:127.0.0.1:7000" BACKENDS="-b 127.0.0.1:9080 -b 127.0.0.1:9081" ALGORITHM="-dl" HTTP_FLAGS="-x -X" TIMEOUTS="-t 10" CHECK_CALLS="-c 10" WEB_INTERFACE="-W 127.0.0.1:7020" #DEBUGGING="-v" DEBUGGING="" $XR $SERVER $BACKENDS $ALGORITHM $HTTP_FLAGS $TIMEOUTS $CHECK_CALLS $WEB_INTERFACE $DEBUGGING
2008-11-18
Subversion 1.5 + default instalation Plone 3.1 buildout: no problems here
I've hit the setuptools + subversion 1.5 problem again with a freshly install Plone 3.1.7 buildout: I've added my egg develop folder in zinstance/src/, I've added the egg in the relevant sections in buildout.cfg, but it wouldn't work because of the incompatibility with the old setuptools version.
The solution is to upgrade the installed setuptools to the latest version. For example, for a standalone Plone installed at /home/tibi/Plone, we have this structure:
/home/tibi/Plone /Python-2.4 /buildout-cache /zinstance
I've changed directory to the Python-2.4 from above and ran:
bin/easy_install -U setuptools
Then I could succesfully run the buildout in the zinstance folder.
2008-07-11
Hosting Plone and Zope 3 applications using nginx
I'm doing a setup on a new server, I've decided to replace the default Apache 2.2 with an nginx http server. The setup which is needed for Zope 3 and Plone applications is the following:
[buildout]
parts =
nginx
nginxctl
[nginx]
recipe = gocept.cmmi
url = http://sysoev.ru/nginx/nginx-0.7.6.tar.gz
md5sum = ae7ce6f66a2cf5a5970d9a9a0da0cf7d
[nginxctl]
recipe = gocept.nginx
hostname = localhost
port = 80
configuration =
worker_processes 1;
events {
worker_connections 1024;
}
http {
upstream z3 {
server 127.0.0.1:8080;
}
upstream plone {
server 127.0.0.1:9080;
}
server {
listen ${nginxctl:port};
server_name z3.example.org;
root html;
include /etc/nginx/proxy.conf
location / {
proxy_pass http://z3/++lang++ro/++skin++myskin/mysite/++vh++http:z3.example.org:80/++/;
}
}
server {
server_name plone.example.org;
include /etc/nginx/proxy.conf
location / {
proxy_pass http://plone/VirtualHostBase/http/plone.example.org:80/t1/VirtualHostRoot/;
}
}
server {
server_name plone.example.org;
rewrite ^/(.*) /VirtualHostBase/http/plone.example.org:80/t1/VirtualHostRoot/$1 last;
location / {
proxy_pass http://plone;
}
}
}
Note: this is a buildout.cfg. Using it together with zc.buildout makes the nginx instalation a very simple process: install zc.buildout (easy_install zc.buildout), and then run buildout in the folder that contains the .cfg file.
The settings in proxy.conf are important. Without a valid proxy_temp_path, for some reason delivery of all content that came from a Plone 2.5 site that used CacheFu setup with no proxy cache was freezing at 16014 bytes. The paths in /var/nginx need to be created and set to be writable by the nginx process (user nobody in my case).
client_max_body_size 0; client_body_buffer_size 128k; client_body_temp_path /var/nginx/client_body_temp; proxy_connect_timeout 90; proxy_send_timeout 90; proxy_read_timeout 90; proxy_buffer_size 4k; proxy_buffers 4 32k; proxy_busy_buffers_size 64k; proxy_temp_file_write_size 64k; proxy_temp_path /var/nginx/proxy_temp; proxy_redirect off; proxy_set_header Host $host; proxy_set_header X-Real-IP $remote_addr; proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
Resources
A more complete nginx sample configuration file (but that only covers how to configure Plone)
Grok guide on hosting Zope 3 with nginx (note, at this moment the document is wrong, the setup line is missing a slash at the end).
2008-04-15
In case you're having problems installing ssl-for-setuptools...
I've stumbled on this error when trying to install a easyshop buildout:
Exception: No SSL support found
An error occured when trying to install ssl-for-setuptools 1.10.Look above this message for any errors thatwere output by easy_install.
While:
Installing instance.
Getting distribution for 'ssl-for-setuptools'.
Error: Couldn't install: ssl-for-setuptools 1.10
After scratching my head for a while, I've found the solution:
# apt-get install libssl-dev
2008-04-08
A tip on debugging Zope 2 with ZEO
I'm having some troubles with CacheFu, and I've resorted to deleting some objects from a debug prompt, which is very easy to get at if one runs the Zope under ZEO. Still, I couldn't delete the objects because I was getting Unauthorized errors. Luckily, there is #plone, from which I got the following tip:
<naro> from AccessControl.SecurityManagement import newSecurityManager
<naro> user = app.acl_users.getUser('admin')
<naro> newSecurityManager(None, user)
Thanks, naro!
Update: I realize now that I didn't write how to connect to ZEO:
#bin/instance debug
or
#bin/zopectl debug
This will connect the ZEO client and drop you in a python shell
2008-03-18
A few ATReferenceBrowserWidget tips
On a Plone 2.5 project I'm working I have a content type that has 3 reference association to another content type. ArchGenXML generated the fields with the same name, which means that in the interface there will be just one field, as they overwrite each other. To have them working I need to rename them, but how to do this from the model? Agx, at first glance, doesn't have support for this. While playing and even trying to change agx to support this use case, I've noticed that agx considers the "association end" as the one meaningful: all tagged values set to it are reflected in the generated case. So the solution to this problem is to set a "name" tagged value in the "end" of the direct associations relationships. Check the following screenshot from Poseidon to see what I mean:
Another issue, this time directly related to the ATReferenceBrowserIssue, is the startup directory support. The widget has support for defaults set in portal_properties/site_properties, a property called refwidget_startupdirectories. The wording of this property's description in the README left me, as a non-native English speaker, a bit clueless. After some digging and debugging, I found out that the format for the lines there is:
/pathA:/pathB
where pathA is a path relative to the Plone site root; when you call the reference browser widget for an object in this path, the second path, pathB is returned as a base for browsing for objects. Even after I have understood the thing about the two colon separated path, it didn't work for me because I was refering to paths with their absolute paths (based in the Zope root) instead of their paths relative to the Plone site.
2008-03-17
GHOP Plone skins overview
Plone has very few skins available from the community, when compared to just about anything. The skin incompatibilities that appeared between Plone versions 2.0/2.1/3.0 further deepen this problem. As a result of the 2007 Plone - GHOP there are some skins placed in the collective, but they're not visible anywhere (they're not published in the PSC, only some of them are available as eggs in PyPI, to get a glimpse of them you need to install them). These skins are placed under the plonetheme namespace, along with other skins, unrelated to GHOP.
To make them a bit more visible (and to serve as a personal reminder for their design), I'm showcasing them here. In reviewing them I've used Plone 3.1 (the trunk of the ploneout package). After each skin was installed and snapshotted, I've uninstalled it and installed the next one.
Click on each thumbnail to get to the full image.
Andreas 01
One of the nicer skin, it stands out through its center align design, different sized columns and its simplicity. I can see myself using this skin as a base for a skin customization.
BlueBlog
This skin, as its name implies, is better suited for a blog, through its tall, thin design. Not a programmers blog though, and that's too bad, as it's a good skin.
Essay
Nice skin, I especially like the portlet design. Somewhat simple, though. If I'd customize this skin, I'd make it wider (maybe make it whole page instead of center-centred)
Green Community
A non-conformist skin, but still good looking. From what I have seen watching the PyPI, it's still under active development. There are some problems with it, though: the login portlet at the top is not fully visible, the "editor" version is missing some bits of the full skin. Still, it could be used for blog-ish type of sites, after some customizations.
Grok
This skin is very similar (might be the same) to the one used for the Grok project website. Probably not a GHOP skin. Although it seems like a very simple customization of default Plone, there are many issues with it that would mean that it would require heavy work to make it publishable for a real website.
Napoli
This is an almost empty skin, no point in showing it here
Pizza
Not a GHOP skin, this skin was created in a sprint. I believe its aim is to be one of the official supported skin. It is somewhat similar to NuPlone. Still needs work, though.
Plone2Kiss
Another empty skin
Python
Very similar to the current python.org skin. It feels rough and unfinished, but otherwise a nice, clean skin.
Relic
Ugly, amateurish skin. Needs a lot of work to get it into something usable. Probably you're better looking for something else.
Sonia
Not a GHOP, it just sits in the Collective svn repository. Promising, but would need a lot of customizations to make it work.
Conclusion: the problem remains: there are very few community-produced plone skins, and the ones available are usually low quality. We, the community, have got to do something about this.
2008-03-13
Tutorial: run ArchGenXML 2.0 under virtualenv
The "modern" (post 1.5) version of ArchGenXML is packaged as egg, available on pypi. While in theory you could run "sudo easy_install archgenxml" and have it running with minimal effort, because it depends on zope.component and zope.configuration, things tend to get muddy and complicated. If you'll "easy_install zope.component" you'll get a bunch of zope eggs installed in python's site-packages and this will probably cause problems. When I've started developing with Zope 3 I had some hard time tracking some problems that ultimately turned out to be caused by zope packages installed in the system python "conflicting" with my regular zope instances. Even the Plone installer prefers to create its own Python directory, to keep the its packages separated from other python packages installed in the system. To solve this problem, ArchGenXML has a mechanism to specify a path to the zope packages, of which I've already blogged about, but I now consider it an extra step which can be avoided by using virtualenv to install the archgenxml egg.
This following recipe is specific to Ubuntu, but probably adaptable to any Linux system, and even Windows. First, if you don't have easy_install in your system, install it with:
#sudo apt-get install python-setuptools
#easy_install virtualenv
In my ~/Software folder I've ran:
#virtualenv agx
This will create a ~/Software/agx virtual environment. We need to activate it:
#source agx/bin/activate
Now all python commands we will run (python, easy_install) will 'belong' to this virtual environment. We can safely install agx, zope.component and zope.configuration, as they will be installed there:
(agx)#easy_install archgenxml
(agx)#easy_install zope.component
(agx)#easy_install zope.configuration
The ArchGenXML egg has defined several console scripts, they're available as scripts "tied" to this virtual python environment, for example, this is the 'archgenxml' script that was installed in my ~/Software/agx/bin folder:
#!/home/tibi/tmp/arch/bin/python2.4
# EASY-INSTALL-ENTRY-SCRIPT: 'archgenxml==2.0-rc1','console_scripts','archgenxml'
__requires__ = 'archgenxml==2.0-rc1'
import sys
from pkg_resources import load_entry_point
sys.exit(
load_entry_point('archgenxml==2.0-rc1', 'console_scripts', 'archgenxml')()
)
What this tells us is that you can safely run this script from "outside" the virtual environment, without needing to first "source bin/activate" it.
2008-01-31
The 763 projects in the Collective SVN
Today I was curious about the number of projects found in the collective svn. They always seemed a lot, but I never knew how many. Until today, when I ran a xpath query over the subversion page and I found that there are 763! This number shocked me, I was expecting at most 200. My number of projects there is very small though, I can only claim ownership over 2 of them.
2007-02-11
First glance at Plone 3
Thanks to the easy plone 3 buildout (plonout), I'm having my first look at the upcoming Plone 3. Some of the more evident changes:
- Versioning is now possible thanks to CMFEditions, which means a "Save as version" option in the edit screen and a "Versions" page on objects.
- The Kupu integration has been improved, the Kupu configlet offering new functions: the possibility to edit the toolbar, a new, streamlined interface to control the resource types and the possibility to replace the reference browser with a kupu drawer. In the edit screens kupu now has an "Anchor" button, which allows anchor insertion.
- The interface hasn't changed at all, at least looking at its surface. Would this mean easy transition from older 2.1 - 2.5 sites to the new Plone 3.0?
- wicked is integrated, meaning you can get easy wiki-like behaviour, "without the aftertaste of wikis"
- The calendar has now a configlet, offering the old ZMI options accessible until now in portal_calendar
- A configlet to specify the default mimetype for editable text fields (Types Settings)
- The 'sharing' tab is back, with an improved interface
- The different views on objects are loaded through AJAX and there's a "Loading" OSD that appears at the bottom of the page
- In the Edit screen there is a "toolbar" at that top that uses AJAX to load several views that gather different settings that were spread among the Edit and Properties screens until now.
- There is now a portlet management engine which allows portlet customizations. To me, at first look, this management page seemed extremely crowded and unintuitive. But this was just the first impression, after a minute of playing I already felt comfortable with it. Unfortunately, there's no "Simple HTML portlet", an option already offered by other portlet engines such as CMFContentPanels and the "Classic portlet" required knowing a template path and a macro nameb, but I'm sure this "Simple HTML portlet" is something that could be easily written. On the plus side, the portlet management engine offers the possibility to place portlets only for a specific group or for specific content types, which couldn't be easily done using CMFContentPanels.
- There is a "rules" option in the action menu on the main page, which leads to several pages that allow defining actions based on conditions, but I couldn't get it to do much and didn't insist on it.
A lot of new, exciting stuff, without even looking under the hood (Zope 2.10, lots of zope 3 technology used, KSS and Ajax). I've encountered several bugs and there are several areas that could be improved, so it would be great if more people would download the ploneout and run Plone 3.0, at least to have a look, play with the new technologies and report the bugs.
I presume that upgrading Plone 2.1/2.5 to Plone 3 would be relatively easy if there weren't many customizations done to the management interface, but this new technology also adds to the complexity of the Plone as application development framework. One last thing, if you haven't learned Zope 3 by now, start right now, it has become unavoidable in developing for Plone 3.
2007-02-06
Better load time for Plone sites
You probably know by now that Plone sites are better suited at content creation that content delivery. Still, the Plone solution is too good to pass even when creating simpler sites, where +99% of the trafic will be anonymous one. And when you have a good hammer, everything looks like a nail.
One of the various problems that Plone has when delivering this brochure type of websites is that the page weight is pretty high. On an average page that loads some images (a logo and a splash image), a Plone page can weight at about 500 kb. Pretty high, especially when the page doesn't seem too "different". The Javascript files loaded for this page are about one third of its weight and probably not used, if your website doesn't use the livesearch, search engine word highlight, internal search word highlight, the icons for external links or any other "gimmicks" that Plone uses to enhance the user experience.
To prevent these files to load for the anonymous user, place the following condition for the undersired javascript files in portal_javascripts:
python: not portal.portal_membership.isAnonymousUser()
In my case, after some testing, I've decided to leave the following files untouched, to make it possible for site editors to login from the site:
register_function.js
plone_javascript_variables.js
cookie_functions.js
login.js
Next, a look at the css files that are being loaded will show some possibility for improvement there as well, but not as dramatic. Many of the files there can be conditioned with the same line as above, but this depends on the type of website being developed.
You can enable the debug mode for both portal_javascripts and portal_css to help observe which file gets loaded. Of course, placing those conditions in portal_javascripts and portal_css will probably most likely increase the load on the server, but the trade-off is probably worth it.
And finally, enabling mod_cache and mod_deflate for the website will help even further reduce the number of bytes needed to be loaded from the Plone site.
2007-01-30
Problems with migrating AT content from Plone 2.0 to Plone 2.5
Latest problem that ate too much of my life already (took me a night to get through) was importing some content from a Plone 2.0 site to a new instance of Plone 2.5. The old content was created using an old version of AT (probably 1.2). To prepare the migration I've created a new content type using ArchGenXML that mimicked the old product name, classes and fields and exported the content from the old Zope instance as a .zexp file.
The process should have been pretty much straightforward, but I hit some problems: the content types for the objects and fields was broken (it was printed as <plain_text at broken>). I had to write a script (which used an ExternalMethod library that I used to examome objects) that changed the content type to text/structured and text/plain on several fields. Next, there were lots of unicode decoding problems that made impossible cataloguing the content. So I ran again a script to convert that content and finally things started to look right.
I believe the problem with the invalid content type was due to the fact that the mime_types package from MimetypesRegistry was refactored (moved or replaced) since Plone 2.0 was released with Archetypes 1.2.
2007-01-12
Firebug getting close to 1.0
Wow! I am impressed. Following a discussion on slashdot I've installed the new 1.0 beta version of Firebug, an extension for web developers. Created by the same author as the classic Dom Inspector, Firebug didn't seem too useful for me until now. The version on the mozilla extensions site is old (0.4), not so featured and to me it seemed to be really buggy. The new version seems to work very good and offers for each area of focus a multitude of information and options that puts it on first place in my toolkit as Plone web developer.
2006-11-07
Getting the parent object in an acquisition context
To get the parent of an object, you'd have to use this code:
myparent = aq_inner.aq_parent.aq_self

