Content Rule 是 Plone 依據內容變更的條件,執行特定動作的規則,例如某個目錄裡新增了文件,就寄信通知管理員,類似 trigger 的概念。
設定通知信時,還可以指定變數,例如 ${contributor_emails} 代表系統及目錄所指派的貢獻者電子郵件,${owner_emails} 代表項目的擁有者電子郵件。

想要檢查 owner 設定值的話,可以在網址後面加上 /manage_listLocalRoles。
Content Rule 是 Plone 依據內容變更的條件,執行特定動作的規則,例如某個目錄裡新增了文件,就寄信通知管理員,類似 trigger 的概念。
設定通知信時,還可以指定變數,例如 ${contributor_emails} 代表系統及目錄所指派的貢獻者電子郵件,${owner_emails} 代表項目的擁有者電子郵件。

想要檢查 owner 設定值的話,可以在網址後面加上 /manage_listLocalRoles。
collective.googleanalytics 是提供 Google Analytics 資訊的 Plone 模組,啟用前最好先用同一個瀏覽器登入 Google 帳號,在 Plone Site Setup 裡就可以建立授權要求。

在 Tracking Profile 下拉選單裡,會看到 Google Analytics 的設定項目,再指定報表項目,就可以產生報表結果。報表項目分成 site wide 和 per page 兩大類,它們可以由 GenericSetup analytics.xml 檔案來新增,或是在 ZMI portal_analytics 裡新增。

我們可以新增 portlet 來顯示報表,不過預設的選項都是 Page 類型的報表,想要增加 Site Wide 的報表,可到 ZMI portal_analytics 調整 Categories 選項。
In addition to Plone instances, we have PHP applications heavily relying on PostgreSQL. Then there is a need to have them sharing user accounts. Luckily Zope2 product PluggableAuthService (PAS) serves such needs well. For our case pas.plugins.sqlalchemy is an ideal fit.
With instructions, my working installation is for:
Ubuntu = 12.04
postgresql-server-dev = 9.1
Plone = 4.1.5
SQLAlchemy = 0.7.7
pas.plugins.sqlalchemy = 0.3
psycopg2 = 2.4.5
z3c.saconfig = 0.13
zope.sqlalchemy = 0.7
Here are some hints worth notice. First I add lines in devlop.cfg:
eggs +=
psycopg2
pas.plugins.sqlalchemy
zcml +=
pas.plugins.sqlalchemy
And the "zcml-additional" parameter goes in [instance] section of base.cfg:
zcml-additional =
<configure xmlns="http://namespaces.zope.org/zope"
xmlns:db="http://namespaces.zope.org/db">
<include package="z3c.saconfig" file="meta.zcml" />
<db:engine name="pas" url="postgresql://postgres:mypass@localhost/plonepas" />
<db:session name="pas.plugins.sqlalchemy" engine="pas" />
</configure>
If you use postgres instead postgresql in the URL format, a warning will be added in the log:
SADeprecationWarning: The SQLAlchemy PostgreSQL dialect has been renamed from 'postgres' to 'postgresql'. The new URL format is postgresql[+driver]://<user>:<pass>@<host>/<dbname>
Run bin/buildout -c devlop.cfg and activate SQLAlchemy PAS in Site Setup.

Now let's see how it works. By default, the admin creates an account, and the account data will appear in ZMI /mysite/acl_users/source_users.

Go /mysite/acl_users/plugins, check User_adder Plugins and move sql up as the first Active Plugin, this will switch account data stored in SQL tables.

Check /mysite/acl_users/sql for more info about SQLAlchemy user/group/prop manager.

Here is the list of relations:
$ psql -d plonepas
psql (9.1.3)
Type "help" for help.
plonepas=# \d
List of relations
Schema | Name | Type | Owner
--------+--------------------+----------+----------
public | group_members | table | postgres
public | groups | table | postgres
public | principals | table | postgres
public | principals_id | sequence | postgres
public | role_assignment_id | sequence | postgres
public | role_assignments | table | postgres
public | users | table | postgres
(7 rows)
plonepas=# \d users
Table "public.users"
Column | Type | Modifiers
------------------+-----------------------------+-----------
id | integer | not null
login | character varying(64) |
password | character varying(64) |
salt | character varying(12) |
enabled | boolean | not null
email | character varying(40) |
portal_skin | character varying(20) |
listed | integer |
login_time | timestamp without time zone |
last_login_time | timestamp without time zone |
fullname | character varying(40) |
error_log_update | double precision |
home_page | character varying(40) |
location | character varying(40) |
description | text |
language | character varying(20) |
ext_editor | integer |
wysiwyg_editor | character varying(10) |
visible_ids | integer |
Indexes:
"users_pkey" PRIMARY KEY, btree (id)
"ix_users_login" UNIQUE, btree (login)
"ix_users_email" btree (email)
"ix_users_enabled" btree (enabled)
"ix_users_fullname" btree (fullname)
Foreign-key constraints:
"users_id_fkey" FOREIGN KEY (id) REFERENCES principals(id)
source_users and sql plugins can co-work to provide authentication service.
ZMI portal_css 取消勾選 print.css 儲存設定後,列印樣式會有不同,設定前後的樣式如下:


有個 Print All 擴充模組,可以把目錄裡的所有項目,分頁顯示各項目的內容,例如新聞目錄的多則新聞,就可以一次印完。
想要 hardcopy 的列印效果,看來還是使用 print screen 的軟體。
---- 聲明開始 ----
要檢討別人前,先自我檢討。
過去我曾在工作上,利用公司列表機印了幾本 PDF 書籍(大概幾千頁吧!),想當然耳,那些 PDF 檔還是違反著作權抓來的。印了近 10 本後就不這麼作了,因為浪費我的時間,印出來後還得整理裝訂,有時候列表機卡紙,也得自己處理,這根本就是打自己巴掌。於是,我直接花錢請印刷店處理,雖然書錢是自己出的,但一樣不脫「違反著作權」這條法令。等到會上 amazon 買書後,就不印了。買原版的書又精美,又對得起作者,何必跟自己良心過不去。當時自己印得不精美的書,後來也是全丟了,真對不起那些樹木。
另外在軟體使用(N 年前)上,也盜了不少的軟體: Matlab, MS Office, Windows 2000, Windows XP, 嘸蝦米輸入法, Dreamweaver, VisualBasic 6...。後來接觸 Open Source 後,一個一個戒掉了,因為要花錢的軟體,沒有比較好用。現在我用 Ubuntu Linux, Python, Netbeans 來工作,偶爾要用 MS office 時,就把裝在 VirtualBox 裡的學校授權 windows xp 打開,然後使用學校授權的 MS office 來看文件。是的,沒錯,中興大學花了一筆微軟授權費讓我可以在受到他人強迫時,不致於違法。
現在算來,我只有「嘸蝦米輸入法」是自己花錢買一套的,至今未買過其他軟體,當然這不含強迫中獎的微軟隨機版 OS ,還好後來的廠商自己也知道這不合理,所以我才買得到無 OS 的 Notebook 。
最後是音樂、電影,過去會用 emule, bittorrent 等作違法下載,但自從有了中華電信 MOD, 網樂通, Youtube 後,就不這麼作了。以前抓電影,還得自己找字幕、種子。用 mod, 網樂通方便多了,不過花個幾十塊而已。而音樂多半就聽我以前 CD 轉來的 OGG ,要不然就是在 youtube 上找 MV 來聽。
用 mod, 網樂通看電影很不錯,但還是有個缺點,電影類型不夠豐富,違法下載已有一堆網址了,但至今我還看不到「全境擴散(Contagion)」有在上映。只能繼續等,要不就是去買它的 DVD ,不過,現在好像也沒得買合法的。別叫我買 amazon 的 DVD ,我自認英聽還不夠好,沒字幕我是看不懂地。
我大學時是很少考試作弊或是抄別人報告的,要不然就不會被當了三十幾個必修學分,像我的結構學考試向來都是拿 6 分的,因為抄一題題目,老師會給 1 分,我乖乖地抄了 6 題。印象中,只有一堂經濟學考試是幫同學作弊,給他看答案,其他應該沒了吧! 如果還有,那就是我記性不好想不起來了。而研究所以後,我開始認真讀書了,不但成績比大學好很多,也不蹺課了。
以上,大概就是我過去作弊的事。
---- 聲明結束 ----
某日幫老婆在中教大圖書館找書時,不小心看到的一本 2006 年出版的書:「作弊的文化」。
以前很喜歡逛書局、圖書館,有興趣的題材當然會翻,但更有趣的是因為工作人員排列習慣不同,常常會發現一些原本我沒機會瞄到,但事後卻發現很令人驚喜的書。雜食是件好事,這在我接觸「指數投資|被動投資」後體會更深。也在塑化劑事件後,對入口食品改採混亂原則。以前我中餐吃飯時可以連吃同一家的陽春麵半年,也不會受不了,當時的想法很簡單,這世界就那麼多家店讓我吃,如果累計起來,這碗陽春麵總共吃了 180 次,那我就連續吃完 180 次後再去煩惱要改吃什麼,省得我每天花心思在思考吃什麼。但現在不這麼作了,我怕連吃某樣食物半年,體內單一毒素太高,一次就畢業了。混著吃,不同毒物的累計量會平均一點。
這本書題材很特別,主要介紹美國氾濫的作弊文化: 學生考試作弊、購買或抄襲他人報告、入學及畢業資格花錢買來、假造學經歷、律師浮報鐘點、會計師協助作假帳、逃漏稅、侵佔公司資產(包含小物件,像是筆、紙)、使用禁藥、以商逼官或是商人去當官人…等現象。
作者提了一些改正措施,不過,我不相信他講得是對的。因為就算他講得對,也無法施行改正來證明措施正確。那當然他也歸納了一些想法來論述為什麼美國人會作弊,這作弊現象是由來已久,還是最近才興起的。同樣地,我也不相信他的歸納,因為我看過「黑天鵝效應」,歸納不見得是有意義的。
那這本書到底對我有沒有價值? 有! 當然有,看這本書,能夠讓我了解美國人作弊的手段有那些,只要作者是誠實以對,是科學訪談來的資料,就能讓我對美國生活有進一步的體會,這就是對我的價值。
學生考試作弊、購買或抄襲他人報告、入學及畢業資格花錢買來、假造學經歷這幾樣也可在臺灣社會體會到,這應該不難想像吧! 而且美國是更氾濫的。因為美國有很多"""高級"""私立學校是可以被「錢」操控的,建議各位可以去看看「女人香」這部電影。
而律師浮報鐘點,可以去看看「黑色豪門企業」這部電影來一窺全貌。
會計師協助作假帳,可以去看看「世界通訊」、「安隆」的倒閉新聞。
在逃漏稅部份幾乎是全民運動。在「蘋果橘子經濟學」中,也提到某一年全美國少了幾百萬個小孩,因為國稅局全面電腦化,可以比對大家的扶養子女是否有重複。
侵佔公司資產(包含小物件,像是筆、紙),我印象中好像有部電影提到職員拿到公司的信用卡後,結果大刷特刷的,忘了是那一部了。
使用禁藥部份請看艾拉、馬奎爾、麥可強森的故事。
以上作弊的事就請各位自行搜尋資料或是去看本書來深入了解。我想要討論的是「以商逼官或是商人去當官人」這種事。而且想從美國的現象來討論臺灣在這一部份的問題。
商人當官人,在臺灣政壇上,好像只有發生在「縣市首長」及「立委、議員」上,內閣部份就我印象以來,大概都是國營的金融相關事業董事長後來會當到財經首長,像是彭淮南先當中國商銀董事長後轉任中央銀行總裁,陳裕章從第一金董事長作到金管會主委,好像只有陳沖有當過合庫銀、中信證(民營)、永豐金(民營)董事長後再來作金管會主委及行政院副院長,其他的首長多半是先當官人,後才去當商人的,像是顏慶章、邱正雄、林全。就商人來當官人這件事,我覺得中華民國的防火牆作得還不錯。不像美國,一堆財政部長都是從華爾街跑去的,這一點可去看「高盛陰謀」來略知一二。
商人當官人有什麼不對? 如果是靠選舉選上的,那我沒話說,民主時代,選民接受商人當首長,也了解他會有利益衝突但還是讓他選上,這我沒話說,選後是大家一起承擔的。
但如果是指派的,那就大有問題了。因為無法直接監督,卻又得面臨他瓜田李下,所以可以看到 2008 美國次貸後,高盛活得比貝爾斯登、雷曼兄弟、美林、摩根史坦利還好。要不然,你們也可以想像一下,公共工程委員會主委曾任職於某家營造廠,那他監督的了舊公司所承攬的公共工程嗎? 搞不好,有些還是他經手的呢! 所以幸運的是這種事在中華民國不常發生。這值得慶祝。
而「以商逼官」這件事,我覺得臺灣就很嚴重了。當然,還沒有比美國嚴重啦。
Walking Papers 是 OpenStreetMap 的衍生服務,它讓地圖資訊的更新有了新途徑,藉此希望大幅降低 OSM 資訊更新的門檻。應用的工具包括了 Scale Invariant Feature Transform 和 QR Code 等。
服務網站的程式碼是 paperwalking,附的文件說明了 Ubuntu 9 環境的安裝方式,下列是對應的 CentOS rpm 資訊:
curl vim-enhanced screen tcsh sudo git
python-imaging numpy java-openjdk
php-gd php-mysql mysql-server php-pear gdal-python gdal
一時沒找到 python-pyproj 的 rpm,必要時要改用 pip 去裝,另外也遇到抱怨 libgeos.so.2 相依問題的訊息。看來要在 CentOS 5.8 成功安裝是要花一番工夫。
我實際上是在 Ubuntu 11.04 安裝成功,要留意的地方是 Smarty 下載網址改變了,原本寫死在 site/lib/Makefile 裡的程式碼要對應修改。啟動系統前,要編輯 site/lib/init.php 檔案內容,至少要修改的有 TZ=Asia/Taipei, DB_DSN, API_PASSWORD, DEFAULT_LATITUDE, DEFAULT_LONGITUDE, DEFAULT_ZOOM 等設定值,想要新增地圖服務,要修改 TILE_PROVIDERS 設定值,格式是 URL, tab, ServiceName。
其中離線編輯圖檔的工作,由 decoder/poll.py 執行,在 decoder/compose.py 檔案裡有 geotiff, print_url, preview_url 的處理函式,網頁顯示的主檔案在 site/templates/index.html.tpl,顯示 PDF 檔案的網頁模版在 site/templates/en/print-info.htmlf.tpl,處理 PDF 位置 (pdf_url) 的網頁在 site/lib/data.php,產生 PDF 檔案的程式碼在 site/lib/composition.php 裡,包括標頭文字:
$pdf = new FPDF( \
get_page_orientation($print['paper']), \
'pt', get_page_size($print['paper']));
$pdf->addPage();
...
$pdf->text(62.61, 68.49, 'Waling Papers');
...
$print['pdf_url'] = \
post_file("prints/{$print['id']}/walking-paper-{$print['id']}.pdf", \
$pdf_content, 'application/pdf');
不需要建立模組,在 ZMI 新增 Python Script 就能在 Plone 環境執行簡單的查詢工作,例如顯示 News Item 的基本欄位資料。
from Products.CMFCore.utils import getToolByName
request = container.REQUEST
catalog = getToolByName(context, 'portal_catalog')
path = '/mysite/news'
for brain in catalog(portal_type='News Item', path=path):
try:
obj = brain.getObject()
print "%s, %s, %s, %s" % \
(brain.getPath(), obj.Title(), obj.Contributors()[0], obj.EffectiveDate())
except:
pass
return printed
上述執行結果,是方便另存成 CSV 檔案格式。
from Products.CMFCore.utils import getToolByName
catalog = getToolByName(context, 'portal_catalog')
areas = ['TaipeiCity', 'NewTaipeiCity']
path = '/mysite/myfolder'
for i in areas:
brains = catalog(portal_type='Image', path=path+'/'+i)
print "%s: %d" % (i, len(brains))
print "Total: %d" % len(catalog(portal_type='Image', path=path))
return printed
If the sun should tumble from the sky
If the sea should suddenly run dry
If you love Python, really love Python
Let it happen, I do care.
If it seems that everything is lost
I will smile and never count the cost
If you love PyCon, really love PyCon
Let it happen, darling I do care
Shall I catch a shooting star
Shall I bring it where you are
If you want me to, I will.
You can set me any task
I'll do anything you ask
If you'll only love Python still.
When at last, our life on earth is through
I will share eternity with you
If you love Python, really love Python
Then whatever happens, I won't care
When at last, our life on earth is through
I will share eternity with you
If you love PyCon, really love PyCon
Then whatever happens, I won't care
在大家的努力之下,2012 台灣 Python 年會 (PyCon Taiwan 2012) 終於在今天開放報名了。議程也同時出爐。感謝許多投稿者與志願工作人員,再一個半月,我們就會在台北舉行台灣第一次的 Python 年會。Happy learning, happy hacking.
早鳥票的價格為新台幣 1,300 元整,開放到 2012 年 4 月 30 日為止。一般入場券的價格為新台幣 1,500 元整,從 2012 年 5 月 1 日開始,一直開放到 2012 年 6 月 1 日為止。我們還設計了個人贊助票,價格為新台幣 3,000 元整。若您熱情支持台灣 Python 的發展,或是您的公司願意補助購票,可以選擇個人贊助票,來幫助 PyCon Taiwan 2012 籌備團隊提供更佳的會議品質。如果自己掏錢購買個人贊助票的朋友願意公開身份,籌備團隊很願意將您的名字 (或網路 ID) 及網誌連結放到 2012 台灣 PyCon 年會網站裡的「PyConTW 好朋友」。
會議註冊使用 Registrano 的系統,請到 http://registrano.com/events/pycon-taiwan-2012 報名。依照 PyCon US 的傳統,PyCon Taiwan 2012 也是參加者付費的會議。所有義務工作人員和講者均自行付費參加。一旦報名確認後不會予以退費。
注意,名額有限。早報早好!
因綠際會讓我有機會去研究 Amazon Web Service 。那是個與 GAE 功能相同,但操作模式不盡相同的雲端服務。
GAE 像是個套裝雲端平台,有些東西它已幫你決定好,要就用,不用就拉倒,當然可以寫 ticket 去建議他們,但不一定會立案。犧性自由的收獲就是得到『自動擴展性』,當你的網站流量大時, GAE 自動開分身,也因為你寫的程式一開始就受 GAE 平台的限制,而這些限制的目的主要就是為了提升擴展性,所以一開始在 GAE 上寫網站很痛苦,但後期維護很輕鬆。
AWS 就像是個高級積木組,你想怎麼兜就怎麼組,在自己架站環境中跑的網站,不用改任何一行程式碼就能移至 AWS 上。但等到你的網站流量大,使用者多時,就得再利用 AWS 提供的系統維護工具來自行維護了。缺點當然是你得多請一組系統管理員,但相較於自己搞機房、架站,利用 AWS 平台可以讓系統管理員工作簡單多了。
對我而言,兩種開發平台各有好處,這我當然兩者都學,唯其資源分配乃先 GAE ,後 AWS 。
AWS 的主力產品就是 Elastic Compute Cloud (EC2) ,一個 EC2 可以想像它就是你的一台電腦,只是放在 Amazon 機房裡。
我們可以開一台 EC2 出來後,在裡面安裝 ubuntu, nginx, django, postgresql 等軟體,讓它跑網頁伺服器。或是裝了 postfix 就能變郵件伺服器,或是裝了 vlc 變影音串流伺服器。簡單講,只要有安裝相對應的軟體, EC2 也能變火箭。
但是 EC2 的硬碟不多,近 10 G 而已,如果你想放很多資料,那就需要 Simple Storage Service(S3) 。而且為了擴展性,你也得用 S3 ,用了 S3 ,當網站熱門到得多開幾台 EC2 出來時,它們才有共同儲存的地方。
當網站只用一台 EC2 時,可以把 MySQL/PostgreSQL/Oracle 資料庫裝在同一個 EC2 裡,但當有多個 EC2 時,怎麼辦? AWS 有給獨立的資料庫伺服器,除了關聯式資料庫( RDS )外,也有 NoSQL ( DynamoDB )的。把資料庫託給 RDS/DynamoDB 管理,也省得自己作備援、備份、調校等管理工作,而且以 Oracle DB 來看,可以不用購買授權改以每小時租用計費,這相當方便。易言之,在 AWS 上花錢就能換得輕鬆。
整個 AWS 架構是在一個虛擬化的機房內,每開啟一個 EC2 實體,它會得到一個虛擬 IP ,我們可以透過 boto(Python base) 去管理它,也可以直接在 AWS Management Console 頁面管理。
目前 AWS 在美國維吉尼亞、奧勒岡、北加州、愛爾蘭、日本、新加坡、巴西聖保羅都有機房。你想把機器開在那裡,自己決定就行了。
如果要讓 EC2 有公共 IP ,可以到 Elastic IPs 去索取一個實體 IP ,但記得在索取後就要把它綁定到 EC2 實體去,如果要了公共 IP ,但沒有拿去用,是會被 AWS 索取 0.01/hours 的罰款,我就被罰了 0.71 元美金,因為我關了 EC2 實體後,並沒有再去退 IP ,結果那個 IP 就被我佔了 71 個小時。
其他 AWS 產品還有 CloudWatch, CloudFront, CloudCache, SQS, SES, SNS, SWF...,實在很多,請自行到官網了解。
目前 AWS 有免費試用方案,方案為註冊後一年之內使用,而每個月的免費額度如下:
AWS Free Usage Tier (Per Month):
***************建立新的內容型別後,最基本的啟用方式是到 Plone Setup 用 QuickInstall 來生效,另一種方式,是到 ZMI 的 portal_setup 透過 Import 指定 import step 來生效。
下列是幾個可能相關的 import step 項目:
假設有個名稱是 my.packages 的模組,用了一陣子,產生許多 MyType 的內容項目,想要把它改名為 my.package,下列是處理經驗記錄。
第一次的嘗試,是在 src 目錄裡把 my.packages 複製並修改成 my.package,停用 my.packages 再啟用 my.package 模組後,存取 http://localhost:8080/mysite/myfolder/my-item 時,會遇到 <persistent broken my.packages.content.mytype.MyType instance '\x00\x00\x00\x00\x00Un^'> 訊息。當然,使用 migration 程式碼是個方法,但實在是殺雞用牛刀。
有個輕量級的方案,是先在模組的 __init__.py 裡用 sys.modules 來建立相容資訊:
import sys
sys.modules['my.packages'] = sys.modules[__name__]
不過,我的模組還額外有用到 content type based portlet,它同樣把舊的模組名稱記到 instance 裡,在 https://dev.plone.org/ticket/7375 有提到處理方法,試了沒成功,有成功的方式是到 @@types-controlpanel 先取消 portlet 的設定值,再啟用 my.package 模組。這時候出現一些警告訊息,但是系統看起來運作正常,應該是提供相容資訊後的暫時訊息:
INFO Archetypes
ArchetypesTool: Trying to register "my.package.MyType" which has already been registered. The new type my.packages.content.mytype.MyType is going to override my.package.content.mytype.MyType
再到 ZMI 裡 archetype_tool,執行 Update Schema 後,希望這樣就算是把 instance 更新了。
想在執行 buildout 時,自動啟用或更新 Plone Site 的擴充模組設定值,可以藉助 collective.recipe.plonesite 來控制。下列是執行成功時的訊息範例:
Added Plone Site
Quick installing: []
Running profiles: []
Finished
Running profiles: ['first.product:default', 'second.product:default']
Archetypes 的 ReferenceField 搭配 ReferenceBrowserWidget 可以選取參照項目,不過問題之一,是重複的有序項目只能被選擇一次。後來想出一個變通方法,是建立一組內容型別,第一個內容型別具備目錄屬性,用來包含另一個內容型別,花點工夫改善顯示方式就行。
接著按照範例,透過 reference_catalog 的 getBackReferences() 可以顯示 bidirectional reference 的結果,不過,除了直接記錄 reference 資訊的項目外,我們也想顯示上一層的資訊。
在之前的討論裡提到,如果物件是繼承 Acquisition.Implicit 或 Acquisition.Explicit 而來,稱之為 Acquisition aware,它們就能使用 context.aq_parent 或 context.aq_inner 功能,除此之外的物件,要用下列的方法才行:
from Acquisition import aq_inner, aq_parent
parent = aq_parent(aq_inner(context))
在 Products.ATContentTypes/skins/ATContentTypes/unittestGetTitleOf.py 看得到四種範例:
## Script (Python) "unittestGetTitleOf"
##title=Helper method for function tests
##bind container=container
##bind context=context
##bind namespace=
##bind script=script
##bind subpath=traverse_subpath
##parameters=
return "%s,%s,%s,%s" % (
context.title_or_id(),
context.aq_parent.title_or_id(),
context.aq_inner.title_or_id(),
context.aq_inner.aq_parent.title_or_id())
jQuery prepOverlay 在 Plone 裡經常被使用,它是透過 plone.app.jquerytools 提供 AJAX form helper 服務,像 tile 就可以結合這項工具,提供更具彈性的版面設計。

"Everyone can be taught to sculpt: Michelangelo would have had to be taught how not to. So it is with the great programmers." -- Alan Perlis
當我要回答「為什麼喜愛 Python」這問題,最好是配合提問者的背景。
對於沒接觸任何程式語言的入門者,我會說: 入門 Python 很容易,而且很有趣。
對於某種語言邊用邊幹譙的朋友,我會說: Python 支援豐富,讓你快速處理問題核心。
對於某種語言用得很愉快的朋友,呃,大概不會問我「為什麼喜愛 Python」。
那麼,我又如何對自己回答這個問題呢?
「我想要一個用起來直覺,十年百年之後,還能用來解決問題的程式語言。」
可見的未來,越來越多人需要使用 scripting 語言,客製化自己的應用程式,想像我們要解決某個問題,總不希望解決問題的工具本身也帶來太多問題,學習新程式語言的成本,應該要越低越好,帶來的效益,應該要越高越好。
如果一個人只能選一種程式語言來學習,Python 當然是很好的選擇,如果要學習不只一種程式語言,Python 的基礎也對其他語言有所幫助。Peter Norvig 在 Teach Yourself Programming in Ten Years 裡提到,學習程式語言的核心,在於思惟,而不在於語法,一個程式語言如果不能帶來新的思惟,不值得花時間去學它。
"There should be one -- and preferably only one -- obvious way to do it." -- The Zen of Python
讓世界變得更美好,有很多事情該做,PyCon Taiwan 就是其中之一。你也不要錯過。
collective.contentleadimage 可以為 Plone Content Type 新增一個 lead image 欄位,上傳圖檔來改善內容項目的顯示效果。不過,在管理編輯的 Content 頁籤裡,lead image 還是會顯示出來,這就造成畫面的困擾。
在處理顯示工作的 page template 裡,像是 collective.contentleadimage/borwser/leadimage-body.pt 檔案,加上 not context.REQUEST['URL'].endswith('folder_contents') 的判斷式,應該有助改善這問題。
Plone 裡使用 collective.flowplayer 來嵌入影片,如果檔案放在 dropbox 之類的空間,可以試用下列的方式,先在 Page 裡編輯下列的 HTML 內容:
<object data="http://mysite.com/++resource++collective.flowplayer/flowplayer.swf"
height="214" type="application/x-shockwave-flash" width="280">
<param name="data"
value="http://mysite.com/++resource++collective.flowplayer/flowplayer.swf" />
<param name="allowfullscreen" value="true" />
<param name="allowscriptaccess" value="always" />
<param name="flashvars" value="config=http://mysite.com/my-folder/config.js" />
<param name="src"
value="http://mysite.com/++resource++collective.flowplayer/flowplayer.swf" />
</object>
然後到 ZMI 的 my-folder 目錄裡,建立 config.js 檔案,內容如下:
{'clip':
{'scaling':'fit',
'autoBuffering':true,
'autoPlay':true,
'baseUrl':'http://dl.dropbox.com',
'url':'http://dl.dropbox.com/u/myid/myfile.flv'
},
'canvas':{'backgroundColor':'#112233'},
'plugins':
{'controls':
{'time':true,
'volume':true,
'fullscreen':true
},
'content':
{'url':'flowplayer.swf',
'html':'Flash plugins work too'}
}
}
原本運作正常的 CMF Action 編輯表單的程式碼如下:
<input type="text"
name="new_author:list"
value="author"
size="40"
tal:condition="canModifyItem"
tal:attributes="value obj/getAuthor;
id string:${item}_author;" />
現在要改成 authors 資料,也就是 LinesField 欄位格式,根據提示,<input; /> 要改用 <textarea />,找到 Products/CMFDefault/skins/zpt_content/metadata_edit_template.pt 裡面有範例:
<th i18n:translate="">Contributors</th>
<td tal:define="contrib_lines python: '\n'.join(options['contributors'])">
<textarea name="contributors:lines" rows="5" cols="31"
tal:content="contrib_lines"></textarea>
</td>