Friday, September 21, 2018

Alfresco:Share UIで行うコンテンツモデリング

こんにちは。たなかです。

小学生の子供達の夏休みが終わり、給食も始まったのでお弁当作りから解放されました。

長期休暇のあとは給食のありがたみをいつにも増して感じます。

今回はShare UI上管理ツールのモジュールマネージャでモデル作成をしてみたいと思います。
使用しているバージョンは、201707 GAです。


管理ツールのメニューからモデルマネージャをクリックします。

モデルの作成ボタンを押して必要事項を入力し、作成します。



次に作成したモデルをクリックしてタイプとアスペクトを作ります。

まずは、カスタムタイプの作成を行います。


作成したタイプにプロパティを作成します。



続いてアスペクトと、タイプのプロパティと同じようにアスペクトのプロパティを作成します。




各タイプとアスペクトのレイアウトをレイアウトデザイナーで設定します。
レイアウトデザイナーでの設定は必須です。
設定を行わずに有効化しても表示されないのでご注意ください。



自分でレイアウトを設定したい場合は説明に従い設定することもでき、デフォルトレイアウトの設定やデフォルトレイアウトを元にカスタマイズを行うこともできます。

デフォルト設定を適用してみます。



レイアウト設定が完了したら、保存します。


モデルのメニューリストから登録したモデルを有効化します。


有効化されたことを確認したら、

タイプを設定したいコンテンツのメニューからタイプの変更を選択し、設定します。


先に作成したカスタムタイプ(aegif:customType)というタイプがリストに存在しています。

タイプを設定すると文書詳細のプロパティエリアにタイププロパティが表示されました。


アスペクトの管理でアスペクトの付与、取り外しもできます。


タイプがないアスペクトのみのモデルの設定も行なってみたいと思います。


先ほどと同様、レイアウトデザイナーでレイアウトを保存しておきます。


有効化する前は、文書のアスペクト管理で確認しても該当のアスペクトが表示されていません。





モデルを有効化します。


再度先ほどの文書のアスペクト管理を確認すると、有効化したアスペクトが表示されています。
タイプは1つのノードに1つしか設定できませんが、アスペクトは複数設定することができます。

アスペクトを付与してみました。


設定した文書のメニューリストのプロパティエリアに追加したアスペクトのプロパティが表示されました。


一度タイプを設定するとShare UIからは変更ができないようになっているため、
すでにタイプを設定した下記コンテンツはタイプを変更しようとしてもリストには何も表示されていません。


反対にアスペクトは自由に取り外しが可能です。



モデルマネージャで行うコンテンツモデリングでは、簡易的に作成することが可能なので、細かい設定などを行いたい場合はShare UI上からはできません。
英語表記と日本語表記を分けたい場合もcontent-model.propertiesとcontent-model_ja.propertiesのようなファイルを言語別に用意して各ファイルに設定する必要があります。

Share UI上でモデルを作成し、モデルのアクションメニューからエクスポートを行うと作成したモデルのxmlファイルがダウンロードできるのでそれを利用して詳細を設定する、ということも可能です。


今回は、Share UIから設定するコンテンツモデリングについてご紹介させていただきました。

Wednesday, August 1, 2018

Demystifying Liferay categories: leftCategoryId / rightCategoryId

Liferay allows site administrators to define a "vocabulary" containing categories such as:

  • Cheese
  • Bread
  • Butter

Web content can then be classified using these categories, for instance a news article about canapé would be assigned the categories "Cheese" and "Bread".

Create a Liferay page, put a "Category Navigation" application and an "Asset Publisher" on it, link them and voilà! You have a nice page where relevant articles appear depending on the category you clicked.

Categories can have sub-categories:




Left and right


When you click on a category, you will notice this parameter in the URL: categoryId=21434

You can inspect this category by putting it in the "parentCategoryId" field of this Liferay API page:
https://yourserver/api/jsonws?signature=%2Fassetcategory%2Fget-child-categories-1-parentCategoryId#serviceResults

You will notice that each category has a "leftCategoryId" and a "rightCategoryId" field. What are those!?

They help Liferay easily display items in the category navigation widget. Here is how they are stored in database:

mysql> SELECT leftCategoryId, rightCategoryId, name FROM AssetCategory WHERE vocabularyId=21431 ORDER BY leftCategoryId;
+----------------+-----------------+-----------+
| leftCategoryId | rightCategoryId | name      |
+----------------+-----------------+-----------+
|              2 |               7 | Cheese    |
|              3 |               4 | Camembert |
|              5 |               6 | Roquefort |
|              8 |               9 | Bread     |
|             34 |              35 | Butter    |
+----------------+-----------------+-----------+
5 rows in set (0.00 sec)

When you click on a category, for instance "Cheese", Liferay will use the category identifier to get the Cheese row, and get the left and right, here "2 and "7". Liferay will then use these identifiers in the following SQL request:

SELECT categoryId, name FROM AssetCategory WHERE (groupId = ___) AND (leftCategoryId BETWEEN ___ AND ___);

... where the first blank is the Liferay site identifier, and the second and third are the first and last categories of the vocabulary, in our example 2 and 7. Let's run it:

mysql> SELECT categoryId, name FROM AssetCategory WHERE (groupId = 20181) AND (leftCategoryId BETWEEN 2 AND 7);
+------------+-----------+
| categoryId | name      |
+------------+-----------+
|      21433 | Cheese    |
|      21703 | Camembert |
|      21704 | Roquefort |
+------------+-----------+
3 rows in set (0.01 sec)

Voilà! You get all of the categories whose articles should appear on the page when you click "Cheese".

You might ask: Why not just use parentId to get all categories whose parent is the Cheese categories, and then recursively their own sub-categories using the same technique?
Answer: It would not scale. For vocabularies with n levels of sub-categories, the recursion would trigger O(n!) SQL requests, whereas the left/right strategy uses O(1) SQL requests. This technique is called nested set model. Its drawback is that left/right information must be rebuilt every time an administrator moves or deletes a category.



Applicable to Liferay 6.2 and Liferay 7.0
Nicolas Raoul

Monday, May 21, 2018

Alfresco勉強会を終了します!


イージフの戸谷です。

唐突なエントリタイトルですが44回にわたり続けてきたAlfresco勉強会を終了することにしました。
次回勉強会の日程が設定されていない状態を続けるのも良くないので、ここで終了の理由を書いておきたいと思います。
心配される方もいらっしゃるかもしれないですが、イージフがAlfrescoを扱わなくなる、ということでは全くありませんのでご安心ください!

終了するに至った理由はいくつかあるのですが、その中で最も大きかったことは私を含めた弊社メンバが発表したいと考えていた内容と、参加される方が期待される内容にズレが生じていた、ということでした。弊社メンバはAlfrescoの技術的な(ともすればマニアックな)情報を発表したい。一方で参加される方のほとんどはAlfrescoでは何ができるのか、どういう使い方をするのか知りたいという方が多かったため、結果としてAlfrescoの使い方について毎回説明するセッションを設けつつ、技術的な発表についてはボリュームを少なくするなど調整しながら勉強会を実施していました。ただこれは発表者、参加者双方にフラストレーションを溜めやすい構造になっていたように思います。

そこで今後技術情報については全てこのLaboブログで発信します。そうすることで弊社メンバが伝えたい情報粒度で勉強会の場よりも自由に情報発信ができるようになると考えています。

一方でこれまで勉強会が実質的に担っていたAlfrescoの使い方を知っていただく場については、今後弊社主催のAlfrescoの無料ワークショップという型式で定期的に開催しようと考えています。内容や時期については現在準備中ですので詳細が決まったらLaboブログでも連絡いたします。弊社で取り扱っているOSSのポータルプロダクトであるliferayについても同様に技術情報はLaboブログで発信し、無料ワークショップの開催を検討しています。

型式は変わりますが今後もAlfrescoも技術情報は継続的に発信していきますので、ぜひLaboブログをよろしくおねがいします。

How to install Alfresco 6 on Linux

Hello, I am Nicolas! So, you want to try Alfresco on Linux? Alfresco used to provide a user-friendly wizard installer, but starting from Alfresco 6 they only provide a Docker image. It is not much more complicated, if you follow the instructions below. I have tested on Ubuntu Linux 18.04 and 19.04, if the instructions are different for other distributions of Linux please write a comment, thanks!

Step 1: Install Docker

If you don't have Docker yet, install the package:

sudo apt install docker.io docker-compose

Then add your user to the docker group (replace "nico" with your username):

sudo usermod -aG docker nico

For this change to take effect, either log out and log in again, or just type this into your terminal, as your user:

newgrp docker

Step 2: Install Alfresco

If you don't have Git yet, install the package:

sudo apt install git

Then, as your normal Linux user, go to any folder that has 500 kilobytes of free space (yes that part is very small as it is a kind of installer rather Alfresco itself), for instance your home folder, and execute these commands one after the other:

git clone git@github.com:Alfresco/acs-community-deployment.git
cd acs-community-deployment/docker-compose
docker-compose up

That's it, your new Alfresco is now being downloaded and started! Go have a break.

Using your Alfresco 6

The Alfresco user interface (called Alfresco Share) is at http://localhost:8080/share

The CMIS and WebDAV URLs, as well as some administration tools such as the Node Browser and the WebScripts Home, can be found at http://localhost:8082/alfresco

Alfresco 6 uses Solr to index content, and the Solr console is available at http://localhost:8083/solr

To stop Alfresco, just press CTRL-C in the terminal where you have launched "docker-compose up". This will not reset your changes nor lose your documents. To start Alfresco again, just launch the same "docker-compose up" command in the acs-community-deployment/docker-compose folder.




Going further

As you might have guessed, Alfresco is split into several Docker containers.
To see them all, type the following:

docker container ls

This shows you all of your containers. Have a look at the last column:

[...] NAMES
[...] dockercompose_share_1
[...] dockercompose_solr6_1
[...] dockercompose_alfresco_1
[...] dockercompose_postgres_1

The containers are listed in reverse startup order:
- Alfresco Share (the web interface)
- Alfresco Search Services (the Solr engine and database)
- Alfresco Content Repository (the repository)
- Postgres (the main database)

To see the logs for all containers in real-time, type this:
docker-compose logs --follow share alfresco solr6 postgres

Let's say you want to modify a configuration file or check memory consumption on the Postgres container. Copy the name of Postgres in the "NAMES" column (for instance mine is dockercompose_postgres_1) and paste it inside this command:

docker exec -it dockercompose_postgres_1 bash

That's it, now you have a terminal inside your container!

If you like Alfresco and want to install it on a production server, Alfresco recommends Kubernetes instead of Docker, more on this later!

Tuesday, May 8, 2018

Alfrescoノードブラウザ での検索


こんにちは。たなかです。
定期的に自分の中で編み物ブームが来るのですが、1ヶ月ほど前からまたブームが来ており最近は子供たちに夏用の帽子やバッグを編んでいます。
今編んでいる帽子の毛糸の素材が和紙なのですが、洗えるし軽いから風が吹いても飛ばないと店員さんに聞いて和紙の凄さを再認識しました。

さて、Alfrescoのノードブラウザで行う検索方法をいくつかピックアップしてご紹介したいと思います。
今回利用しているバージョンはAlfresco Community Edition 201707 GAです。

ノードブラウザ は、管理ツールなので管理者が利用することができます。
各ノードの情報を1ページで見ることができるため、タイプやプロパティ、アスペクト、権限情報などを一度に確認することが可能です。




ノードブラウザはShareの管理ツールとPlatformからのアクセスの2通りの方法があります。
Platformからはhttp://localhost:8080/alfresco/s/admin/からアクセスできます。
Platformのノードブラウザ ではノードやプロパティの削除ができたり、結果の最大表示件数の指定ができます。


今回はShareのノードブラウザ をご紹介したいと思います。

adminでログインし、管理ツールからノードブラウザ を開きます。


テキストエリアに検索クエリを入力して、言語を選択し検索ボタンを押すと結果がリストで表示されます。
条件をいくつか入れて絞り込みたい場合はANDを使って条件クエリを追加していきます。(ORの使用も可能です。)

この初期画面からノードを選択してツリー構造の任意のフォルダやコンテンツにたどり着くこともできるので少しだけ先にご紹介します。

ノードブラウザを選択後の初期画面(検索結果が出ている状態ですね)の名前が空になっている方のノード(参照列)を選択します。



次に子の名前がapp:company_homeのノードを選択します。



続いて子の名前がapp:sharedのノードを選択します。
app:sharedが共有フォルダになります。



さらに子の名前がcm:TestFolderInRepo(自分で作成したフォルダです)のノードを選択してみます。
フォルダかファイルかは、子のタイプがcm:folder(フォルダ)、cm:content(ファイル)かで判断できます。




各ノードのページにあるバージョン情報のプライマリパスが下でご紹介する検索のPATHで使える値になります。


◆FTS-Alfrescoによる検索



fts-alfrescoを検索言語に選んだ場合にどのような検索ができるかを紹介してみたいと思います。

●PATHの指定

まずはPATH検索で共有フォルダ配下を取得してみます。
 PATH:"/app:company_home/app:shared//*" と入力して検索!


共有フォルダ配下のフォルダやコンテンツが表示されています。
共有フォルダはよく使うので覚えておくと便利だと思います。

共有フォルダ下にあるフォルダ配下のコンテンツも表示されていますね。
/*とすると、指定ディレクトリ以下全て、という指定になります。

TestFolderInRepoフォルダ配下を指定したい場合は
 PATH:"/app:company_home/app:shared/cm:TestFolderInRepo//*" 
を入力します。
正しく取得されました。

名前

TestFolderInRepoフォルダを除外してみます。
 NOT cm:name:"TestFolderInRepo" クエリに追加します。


除外なのでNOTをつけましたが、NOTをとると・・・

指定フォルダだけ表示されました。


ワイルドカードの*(アスタリスク)を使うこともできるので、『コンテンツ』から始まるファイル名のファイルを取得してみます。
 cm:name:"コンテンツ*" 

指定フォルダ配下の『コンテンツ〜』という名前のファイルが全て表示されました。


作成日

次はフォルダやコンテンツの作成日で絞り込んでみます。
 cm:created:[MIN TO 2018-05-01] 
試しに2018-05-01までに作成されたもので絞り込みました。

MINだけでなくMAXやNOWなども使用可能です。

範囲指定ではなく日付指定の場合は
 cm:created:'2018-05-01'  のような記述で検索できます。

 

作成者

フォルダまたはコンテンツの作成者で指定してみます。
 cm:creator:"*collaborator" OR cm:creator:"*contributor" 
ANDばかりだったので、ORを使ってみました。

今回は*を検索ワードの前に使用してみました。
ここではcollaborator, contributorはもちろん、acontributorなども作成者のコンテンツが取得されました。

名前、作成日、作成者をご紹介しましたが、他にも
編集者(cm:modifier
編集日(cm:modified
タイトル(cm:title
説明(cm:description
なども利用可能です。
基本の構文を覚えてしまえば適宜変更するだけなので簡単です
 

タイプ

 TYPE:"cm:content" を入力すると、コンテンツタイプのものだけ取得できます。
cm:folderだとフォルダになります。

アスペクト

付与されたアスペクトで検索してみます。
 ASPECT:"cm:dublincore" 

noderefによる検索


検索言語にnoderefを指定して検索を行います。

フォルダやコンテンツを作成すると必ずNodeRefというものが作成されます。
そのNodeRefはユニークなのでそれがわかれば一発で目的のノードにたどり着くことができて便利です。

ちなみに、先に紹介したfts-alfrescoでもNodeRefを使って検索することができます。(私はnoderefを選択しているのでほぼ使わないですが・・・)
 ID:"workspace://SpacesStore/999xxx〜" 


Alfrescoで実行できる検索クエリはまだたくさん種類があるのですが、今回はその中から使う頻度が高いと思うものをご紹介させていただきました。