Opportunity for better workflow/content moderation support in Core

Events happening in the community are now at Drupal community events on www.drupal.org.
jstoller's picture

The upcoming Drupal 7 update brings with it a great opportunity to provide better support in Core for advanced workflows with content moderation, but the code freeze is fast approaching and this opportunity may pass us by. I encourage all developers to check out Support Revisions in Different States in the Drupal issue queue and lend a hand.

Why you should care?

The lack of support for comprehensive content moderation in Drupal is a major limitation when considered for use in enterprise, government and many non-profits. These institutions require workflows that not only manage a node's journey to publication, but also manage the updating of that node's content post publication. For instance, how can I edit the "About Us" page of my website, without ever taking it off-line, when all modifications must be reviewed and approved by one or more managers at my institution. Some contrib modules—like Revision Moderation and Revisioning—have attempted to address this deficiency, but until there are some fundamental changes in Core their efforts will continually fall short, hampered by limited features and difficulty integrating with other contrib modules.

What is being proposed?

I have proposed changes to the node system in Drupal so that different revisions of the same node can be in different defined states. A default Drupal installation might only include draft and published states, but the solution is flexible enough to handle an arbitrary number of states. And different content types could each have their own set of states associated with them, allowing for multiple workflows on the same site. This would provide all the building blocks necessary for modules like Workflow and Rules to implement advanced publication workflows, with complete control over who can view/edit/approve any given version of a node over that node's lifetime. And because Drupal itself would be "state aware," problems with integrating multiple contrib modules in a complex workflow would be greatly minimized (just try using Revision Moderation and Workflow together today).

What is needed?

In a word, Developers! I have taken the task about as far as I can, being a front-end/user experience guy. The proposal has received a lot of positive support in the issue queue, but we need some developers to step-up and tackle the coding. I'm hoping some of you with a vested interest in improving Drupal's workflow support will be up for the challenge. Please read the issue, contribute what you can and make the world a better place. :-)

Comments

Translations the right way!

AlexisWilke's picture

One thing that more and more States are doing (and businesses) is translate their content (Spanish and several Asian languages.) That needs to work properly!

What I mean by working properly is working a lot better than what I have in Drupal 6 with i18n which is completely broken.

The idea is simple: You have ONE node and X number of revisions AND translations. In other words, if you have 7 languages, you still have just one node and depending on the currently selected language, I see the corresponding page content. At this time, with i18n in D6, you'd get 7 nodes. Not only that, 7 menus, 7x all the tags, etc.

This brings me to the next problem: EVERYTHING needs to have a language parameter. At this time the node revision has a language so we should be good with nodes. But Taxonomies and their terms need it, menu and menu items, etc. etc. etc.

Once ALL of that is done that way, I will be able to create usable multi-lingual websites for my customers.

There you go. 8-)

Thank you for your consideration.
Alexis Wilke

P.S. What I mean is that the Unicity should be set to unique(nid, language) and not just (nid) [or whatever identifier you may be dealing with, vid, tid, uid... -- although it may not apply to users and some other types.)

branch/'gather' workflow...

chrisgnicholas's picture

One thing that would be really useful in the workflow module, that may well be there already, but is not apparent to this new-to-drupal-workflow person, is how to conditionally route a piece of work to different roles. For purposes of this discussion, we'll say a node can be a container of work. That way we could re-use workflow definitions, but things would route according to, say, which country things happened, or what subject matter we are talking about. We run workshops all over the world, with different coordinators, and would like to re-use the same basic workflows, but restrict work items to the appropriate teams.

The other is how to perform "join" operations on multiple pieces of work, and/or subgraphs. One state might spawn several sub-tasks: make sure you have the fire dept, the police dept, and the hospital records approved for release before calling a hearing, etc.

I'm coming from the JBoss/Jbpm world, and an excellent language for this stuff is jpdl, as per: http://docs.jboss.com/jbpm/v3.1/userguide/en/html/processmodelling.html

In general, thanks for creating such an environment!!

Minimal Change?

mradcliffe's picture

Putting aside the translation bit for now...

Wouldn't it be possible to accomplish this by making it possible to choose which revision is the revision listed in the node table? And providing a UI to edit a specific revision and make that revision 'current'?

This would require minimal changes, but ignores the translation request above. Which may be misplaced as translations could have their own revisions (?).

Not quite. That might be an

jstoller's picture

Not quite. That might be an option if we were just talking about a basic two-state workflow, but I don't believe it would be enough to handle more complex processes. For instance, my proposed use case involves six different states. Each state would have its own rules governing which roles can view/edit it, which other states it can transition to and which users can initiate any of those transitions.

I think that model would be

mradcliffe's picture

I think that model would be better left to contrib rather than core.

Core needs to be able to support the ability to make contrib modules that make these workflows possible, right? Not be the be all, end all of solutions.

There are a number of approval modules out there (I have one, albeit in its infancy).

I'm going to switch to the issue queue with some thoughts / flow chart.

Translations under one node

jstoller's picture

@Alexis: It seems to me that each translation would still need its own revisions/comments/state designations/etc. In fact, each translation of a node should be able to have a completely different workflow. That way you don't have your English speaking editors mucking with your Korean content. With that in mind, I don't think it makes sense to put all translations under the same node. Instead I'd propose a higher level "node group" construct, or something along those lines. That would allow you to indicate that a grouping of nodes actually contain the same content, just in different languages. Of course, I thought that's essentially what the tnid field in the node table is supposed to do.

OT but I agree

toemaz's picture

I completely agree with jstoller@drupal.org on the matter of the translation workflow. The current implementation is solid and has earned my complete trust, at least for my Drupal i18n installs. As an example: http://musescore.org The interface is available in many languages, but the nice part is the wiki handbook (book node type) which is translated in 8 languages. Each non English book page contains the files from the source English one - files are synced when the English version is updated - but it also contains language specific files which are not shared between the translations. This setup works flawless.

Translations: nodes, menu items, etc.

AlexisWilke's picture

@JStoller,

Hmmm... That won't help me. I guess one day I'll write my own version. 8-)

Note that each revision could include a language AND a status.

In my ideal world, when I edit a node I see the following:

  1. The existing body of the original and/or any translation that I'm interested in READ-ONLY mode

  2. The Body edit box used to enter the translation I'm working on

The body of the translation could include a status flag or something of the sort (i.e. could be a more detailed state such as: not available, needs work, partially translated, done.)

Now that would need to be repeated for each element that needs translation (i.e. menu items, terms, etc.)

Thank you.
Alexis Wilke

@toemaz,Might work okay

AlexisWilke's picture

@toemaz,

Might work okay with books. 8-)

I had to create menu links for my pages, and if you create 1 page with 3 languages, you get 3 menu entries. If I create 100 pages, I now have 300 menu entries. If I want to change a menu to point from page A to page B, I have to remember to change 3 of them. Similarly, if I put links in my pages, the translated version needs to be the correct link: from page B(1) to page B(2) instead of page A(2) even though the name should be exactly the same, since only the content translated!!! Yes, here the path URL was not working correctly at all for me. I could not save two nodes with URL "home" since that meant having duplicates. This means the following breaks:

http://www.turnwatcher/en/home
http://www.turnwatcher/es/home
http://www.turnwatcher/fr/home

And anyway, I want users to write that:

http://www.turnwatcher/home

and the system to use their language of choice. But the way it is now, it breaks completely since only one node can have a URL named 'home' (which btw makes sense 8-), I'm happy with the URL path feature--but if you need 3 nodes, it breaks badly.)

Of course, you will say that in French I should have this:

http://www.turnwatcher/accueil

and in Spanish that:

http://www.turnwatcher/inicio

That breaks the <front> page feature now.

So... nothing works the way I would want them to work in the current state.

Now with 3 languages, it may not be too bad, but imagine someone with 10+ languages. That's a killer. With 100 pages x 10 languages you get 1,000 nodes, 1,000 menu items, 1,000 URL paths, etc. And if your links are correct after that, you're darn good! Then, try to change a few pages and their links...

I had only about 20 menu items in 3 languages. That's 60 items. And I was already quite annoyed. Now were I still using i18n, my menu would be about 60 items long. Does that make sense? And again, if I want to change one link to go from Page A to Page B.... I have to do it 3 times editing that menu with 60 items which as you may know is dead slow to load. I'd much rather have 20 items and when I edit see the 3 languages right there!

Now if you look at i18n, it also includes many other things such as blocks, and profiles, and this and that... A total killer.

Btw, if I wanted to do it the way you are talking about, I would not even need i18n. I could simply create 3 x everything and manage 3 x more everything (or even easier: create 3 websites!) So, what I'm asking is to make it so that's actually useful. 8-)

Thank you.
Alexis Wilke

I know this is not the issue of this thread...

pkej's picture

Alexis, I'm totally on the same page as you, and I was just creating a site for two languages. The issues are infinite:

images - not synchronized until just this last one or two weeks.
popup image selectors (image browser, image assist, imce) not knowing about image fields, just images
views - images not synched between different views; need to weight images manually to fit user needs, because there is no way to move them up and down consistently within draggable views and similar solutions.

At least, finally, images are synched, so I can use an wysiwyg editor with a popup image selector. And there is ipetranslator for showing content side by side (at least it seems to do that, though I haven't made it work, but this guy seems happy).

There also is translation table which at least takes away the need for 3x menus and 3x taxonomy (I would have thought you knew of this module, it isn't that new).

Just to commiserate and to offer a couple of solutions.

But all in all it is a multidimensional problem, which unfortunately seems under appreciated by most of the community, which also is true for a lot of other systems I've tried. The problem is that Drupal is one of the cleanest implemented systems that I've found, and has the most going for it therefore it is such a big shame that there is no push to take these needs into consideration at the core level.

@Alexis, I believe I

jstoller's picture

@Alexis,

I believe I understand your issue, but I still don't think associating different languages with different revisions of the same node is the way to go here. To me that just sounds like a recipe for disaster. It seems like you'd be better off making some adjustments to the menu system so that menus and path aliases could reference a tnid instead of a nid. For instance, take your typical Drupal query which is of the form /node/16. Couldn't you create a module that allowed Drupal to understand queries of the form /tnode/16? This would indicate you want the node with a translation set ID of 16 in the user's currently chosen language. So /tnode/16 might be equivalent to /node/16 in English, /node/52 in Spanish and /node/58 in Chinese. That way you only have one menu item per translation set and you can define a single path for which will respect your different languages. All this without breaking the node revision system, so you can still have different workflows for different languages. That is something I would wholeheartedly support as a Core enhancement.

A brilliant solution

pkej's picture

It seems like a feasible, and not too hard to implement solution. It would probably get rid of a lot of the bugs that has been plaguing i18n modules.

I'm a kind of quitter coder, I start coding with good intentions, but abandon the project pretty fast :), but without looking at Alexis profile I do think I've seen contributions to modules, and perhaps even project leadership on some modules. The gauntlet is thrown, and perhaps Jose Reyeros should be brought into this for a possible solution for 7.x i18n...

Getting back to the original

jstoller's picture

Getting back to the original topic here, I've created a new task in the Drupal queue: Add status/promote/sticky to node_revisions table. It is far less ambitious than Support Revisions in Different States, and hence far more likely to make it into D7, but it still would be an enormous step forward. If there's anything you can do to help, please do so.

Is there an issue with

curtaindog's picture

Is there an issue with throwing CCK fields at the problem? Everything lives on the same node and people just see want they want to see (with CCK access). Perhaps the same could also apply to stickies and promoted nodes, just replace CCK in my preceding lines with Views...

CCK fields

AlexisWilke's picture

curtaindog,

Good analogy. The main problem is that all the CKK fields are saved in the node.data field. In itself, it isn't a problem, but if you consider a node and its content, you have to think of a page that's 10Kb in one language (and that's still small). Now if you were to translate that in 10 different languages, that's 100Kb. Loading that node will be slow whatever the language...

So you'd certainly want the equivalent of revisions including a language in the key (rid + lid).

As it was brought up, this would also require changes to all the other modules, and yes it does. Taxonomy, Menu, and any other module that includes text that the user can enter by hand.

There are many modules that will let you change a label, on purpose because you may want to translate the label. That's a real weak way of doing things since you can just have one language. The translation module is a very good solution for that, but that same module is not usable for a whole node content, and even for menus and taxonomy items which can include a description.

Yet, the analogy shows clearly that there is a need for such a system, possibly in the core.

Thank you.
Alexis Wilke

"Language" field

AlexisWilke's picture

Now, I had a thought yesterday morning in this regard.

At this time, we have a textfield and a textarea in the form API.

Imagine we add a couple of new types: translatabletextfield and translatabletextarea. (maybe we'd want something shorter though)

Now the core would be aware that this specific field can be translated! Wow! And when you present it in the Admin screen, you can open one textfield per language that the person is supporting (say for instance that I want to write French & English, then I can select those two languages somewhere. Then each time the core hits a translatabletextfield, it shows me two fields: one for the French textfield and one for the English textfield.)

Then the core takes care of saving that text in a table and returns just an identifier to the module (such as the taxonomy module). That identifier is unique, whatever the language. The text table would be something like this:

. tid SERIAL
. language CHAR(2)
. data TEXT

tid is the text identifier

language is the language of this text

data is the actual text

Now a module needs the text, it calls one function with the language being optional. When not specified it uses the user selected language, if Anonymous, it uses the browser selected language. (note: the user should have the capability to tell Drupal to use his browser default and fallback languages).

. drupal_get_text(tid, language = NULL)

That's it. Very simple and it makes the entire system work in a way that's so much easier to handle than this crazy i18n implementation... Man! Am I dreaming again?! Finally a working translation system in a CMS?

Anyway... 8-)
Alexis Wilke

Hi Alexis, Thank you for your

curtaindog's picture

Hi Alexis,

Thank you for your informative response. I suspected there might be some performance nasties lurking around in my suggestion... even so I'm currently thinking of following through on that approach in a highly customised workflow I'm setting up... if it falls over I'll know what to blame!!!

With regards to the Language field my gut tells me this should be somehow incorporated into the input filter system, but I'm not up to speed with i18n considerations so I could be completely off target.

Wiki

Group organizers

Group notifications

This group offers an RSS feed. Or subscribe to these personalized, sitewide feeds: