Closed (fixed)
Project:
Taxonomy Access Control
Version:
7.x-1.x-dev
Component:
Integration with other modules
Priority:
Normal
Category:
Feature request
Assigned:
Unassigned
Reporter:
Created:
7 Jul 2011 at 10:15 UTC
Updated:
7 May 2014 at 15:11 UTC
Jump to comment: Most recent, Most recent file
Comments
Comment #1
xjmOh, you must be with the guys in Austria. :)
I'm not sure what might have changed since Drupal 6 in this regard. However, my first thought is to do away with view_unpublished, and instead replace core's published/unpublished functionality with a term reference field:
hook_form_alter()or the like.)So, in your example, Role B would have Allow/Ignore/Ignore for Unpublished, and Allow/Allow/Allow (if deletion is allowed) for Term A.
Comment #2
xjmOh, forgot to add, your administrative roles (whichever ones are setting nodes to unpublished in the first place) would need the Create grant for the Worfklow state vocabulary default, but normal authenticated users would not. No roles should have the List for this term.
Comment #3
sebastian.haas commentedYep! :)
Thank you very much for your time and efforts, I appreciate that. I also thought about doing a solution view_unpublished independently which actually seems to be the much more painless approach than fixing that issue as well as it would not provide really _new_ functionality-
However, I have to double check that with my chief since it's not me who has to live with that setup and it's charactaristics for the next few years. :)
I'm setting status to postponed until I have an direction to go- Maybe I find some time to dive into that subject and get an idea of how much work would have to be spend on that module integration.
Comment #4
sebastian.haas commentedstatus changed
Comment #5
sebastian.haas commentedThe reason for using view_unpublished in our case is http://drupal.org/project/scheduler which depends on the drupal core field published/unpublished.
So I have to reopen my request and will try to get more information about what is causing that issue.
Comment #6
sebastian.haas commentedreopened request
Comment #7
xjmAhh, that makes sense. Yes, a simple workflow vocabulary will not work in this case.
Be sure to take a look at http://drupal.org/node/765832 (which is based on LTE Drupal 6 but is mostly still applicable). We might want to make a little helper module with a hook_node_grants_alter().
Comment #8
sebastian.haas commentedToday I found some time to take a look on the subject. It think we should definitely think about a better integration of the published/unpublished state of nodes since its a core feature...
For example: If I have the authenticated users (which is tac's default setting) and also anonymouse users role set to View=Allow, this completely removes the published/unpublished functionality because of the following to lines, inserted into table node_access:
11 1 term_access 1 0 0
11 2 term_access 1 0 0
where 11 is my unpublished node's id and gids 1 and 2 are standing for anonymous users and authenticated users.
So besides of the fact whether a node is published or not it will become accesible through tac. So maybe it should be possible to define different behaviour if it's an unpublished node.
Another approach would be to let tac completely ignore $node->$status like its implemented now and only restrict access to unpublished modules via another module.
However, I would appreciate if you could get the current behaviour across to me... For rid 1 and 2 (anonymous and authenticated users) tac writes permissions into node_access no matter if a node is published or not but for roles depending on tags it only writes permissions if the node is published. So, to extend my previous example if I have tagged node#11 and configured tac in a way that role#6 has update=allowed for that term I get the following additional line if I publish my node:
11 6 term_access 0 1 0
This line is getting removed from node_access if I unpublish node#11.
Thank you.
Comment #9
xjm(Removing tag as this is not a release blocker.)
TAC doesn't check
$node->statusat all, and should not alter or override the core behavior. Keep in mind that TAC is actually currently supporting the core feature (since the core philosophy is that only administrators can access unpublished content), and it is view_unpublished that deviates from the core behavior.The correct solution to integrate the two modules will be a
hook_node_grants_alter()so that TAC can override view_unpublished's0forgrant_update. We might also want to abstract this case to integration with other node access modules.This is strange. There is no code in TAC that would make this distinction. This behavior could even be coming from
node.module. I will need to look into it further.Comment #10
sebastian.haas commentedTAC doesn't check $node->status at all, and should not alter or override the core behavior.
But because tac doesn't check $node->status it grants view permissions like for any other published note which does override the default core behaviour in my case as it doesn't matter whether a node is published or not, it's treated the same way. So with tac enabled, there is basically no use for a node's status anymore as all nodes are being published because of the View=allow permission-
Comment #11
xjmI was about to reply that this is not correct... then I tested it and confirmed it is correct. In Drupal 6 and prior, the node published state overrode any and all node access grants, from any access control module, so TAC could not grant access to unpublished nodes, no matter what. That's why
view_unpublishedcame into existence. The fact that this appears to be different in Drupal 7 concerns me, because if I was not aware of it as a developer, I am certain many users will also not be aware of it. I am not sure if it is an intended core behavior change; I need to look into it more.Edit: This is probably the reason for the difference between the Drupal 6 and Drupal 7 behavior with view_unpublished. Now view_unpublished is just another node access control module, and so collides with TAC in the grants table like any other node access control module. So the correct answer is still a
hook_node_access_alter().Comment #12
xjmFound #920614: Unpublished content visible when a Node Access module is enabled, which is marked fixed, but... I will try to get some answers on this from core developers today.
Edit: http://drupal.org/node/920614#comment-3499932 is enlightening.
Comment #13
sebastian.haas commentedSo what can I expect from tac in case I have to develop some helper module. Will the current behaviour remain in the d7 release?
But no matter if tac overrides unpublished nodes or ignores them, we will have to fix that issue I posted in #8 at the bottom because it makes it impossible to control unpublished nodes via terms.
Comment #14
xjmI would have marked it "Won't Fix" if I wasn't going to work on a solution. :) I just need to fix all these form errors first (#1214472: Undefined index: und in taxonomy_access_form_alter() -- incorrect assignment of language key etc.), and (now) get feedback from some core folks about what the design behavior of the unpublished state is.
Comment #15
xjmDamZ explained this to me. A separate issue has been opened at #1216212: Do not indiscriminately override unpublished state. How we handle that will dictate the solution to this as well.
Comment #16
xjmAfter thinking about this a bit, I think that maybe the best solution would be for TAC to provide a permission, "Use TAC grants for unpublished nodes" or something. That'd eliminate the need for view_unpublished entirely.
Edit: code snippet was incorrect. However, it would still be simple to implement.
One would simply add this permission to the given role at
admin/people/permissions. What do you think? Would this work for your use case?Comment #17
sebastian.haas commentedSounds good although I'm not sure if I fully understand what you're saying.
So I just write down a few ideas of mine:
But we still have to fix the issue from post #8.
Comment #18
xjmTry testing the patch in #1216212: Do not indiscriminately override unpublished state and seeing if it can provide the behavior.
admin/people/permissions#module-taxonomy_accessadmin/reports/status/rebuild. (This step is necessary due to a deficiency in the patch; for testing, rebuild each time you change the permissions atadmin/people/permissions#module-taxonomy_access).Comment #19
sebastian.haas commentedSee last post of http://drupal.org/node/1216212
Comment #20
xjmSo, based on #962664: Taxonomy Index for unpublished entities, here is what I think an interim solution will have to look like.
taxonomy_access_unpublished.hook_query_TAG_alter()on TAC's node access queries to make it use TEI the table instead of{taxonomy_index}. (Aside: This function would be namedtaxonomy_access_unpublished_query_taxonomy_access_node_access_alter(). Yowza. I wish for the hundredth time the module were namedtacinstead oftaxonomy_access.)hook_node_access_records_alter()to update TAC's grants to the logic we originally provided in #1216212: Do not indiscriminately override unpublished state.This is a not-insignificant undertaking, so I don't know how soon I could work on it. The roadmap is there, though, if you want to try your hand at a patch.
Comment #21
sebastian.haas commentedAd 4.: I think this is not possible in that way because of
since I cannot alter a query which is never built... Are you sure you meant
taxonomy_access_unpublished_query_taxonomy_access_node_access_alter()?Comment #22
xjmWhy do you say the query is not built? That function calls TAC's query builder. The change needs to be module-wide because we are entirely changing the database table used.
Comment #23
sebastian.haas commentedOh I think I understated my point. Whatever, I have written a small module that depends on taxonomy_access and taxonomy_entity_index which does exactly what I want here.
It's a slightly different approach than what you described in #20, but as I mentioned I don't think
hook_query_TAG_alter()will work in that case. I'm also using the node_entity_index table for unpublished nodes only, so 90% is done by tac- I'm using almost everything of it's api to build permissions.I can upload the module here if you want me to-
Comment #24
xjmEdit: I think I understand the confusion now. My suggestion was to add the query alter and make your own call to
_taxonomy_access_node_access_records()in thehook_node_access_records_alter(). You need to do this so the submodule is robust. Otherwise it will break any time the query is used outside this specific case. Edit: the affected nodes queries would also need to be rewritten as dynamic queries and tagged, I think. Otherwise your nodes will not be updated properly when there are taxonomy or configuration changes. Edit 2: looks like they are already dynamic, so they just need a tag added.Ping me on IRC if you like and I can explain further.
Comment #25
xjmI just want to reiterate if you create a submodule without including the query alters, it will make your node access broken whenever any change is made other than via
node_save(). Say, if the user changes a role's TAC configuration, or deletes a taxonomy term. All the other queries will not select from the unpublished nodes' relationships.Comment #26
xjmI posted #1220610: Tag all queries on {taxonomy_index} so that all queries against
{taxonomy_index}can be tagged withtaxonomy_access_nodeand thus manipulated from another module.Comment #27
sebastian.haas commentedThank you for #1220610: Tag all queries on {taxonomy_index}, this made my life much easier. I think the global query alteration could be done like this:
Iterating over the conditions array might be unnecessary since I did not found any other occurence of
ti.nidthan in_taxonomy_access_node_access_recordsso the array size should be constantly 2...Comment #28
xjmYep -- though the new tag is more generic, so we thankfully got the hook name down to
taxonomy_access_unpublished_query_taxonomy_access_node_alter().I would keep the foreach loop, as it makes the hook more robust going forward as new functionality is added. Actually, for best practice, we probably want to loop over
$tableslooking fortaxonomy_indexand collect those aliases (since it is possible to join on the same table twice), then set them to the new table.Also, I did not realize that TEI names the id field differently (though... of course, it has to). This means we need to check not only conditions, but also fields and joins, and replace the nid with
$alias.entity_idas you have above.Comment #29
sebastian.haas commentedThanks for your input.
I extended the code from above:
This solution should also be alias-independent as I cached them for later use.
What do you mean by checking joins? I don't think it is necessary/possible to check them explicitly as there is a
join typefield in the$tablesarray that defines the type of join. I attached a screenshot of the $tables array to illustrate this.I also implemented
hook_node_access_records_alter()and wrapped everything into a module with a dependency to tac and tei. But since I'm about 10 days into drupal community I don't really know what to do next. I can post my code here or give it to you to integrate it with tac or to open a new module, or I can open a new module on my own.Or in case you're thinking it's not useful/practicable at all, I can just forget about it and only use it internally.
Comment #30
xjmThe code above looks like the correct solution as far as I can tell at first read. Regarding the joins, when you complete the modifications in the hook and do a
$query->__toString(), does it correctly use the new table in in that query even when the table is not the mainFROM?It's definitely worth using as a TAC extension module until #962664: Taxonomy Index for unpublished entities is fixed. I can maintain it, since ideally I'd like to integrate the functionality into TAC once TEI is no longer required. Go ahead and upload an archive of it as an attachment here once you're ready so that I can review it.
Comment #31
sebastian.haas commentedad query: Looking good to me as far as I can tell. (see screenshot)
ad module: I attached a basic version of taxonomy_access_unpublished, but there are still a few tasks to do... I'm going to post them in the issue tracker as soon as you open the new module.
//EDIT: Ahm.. I forgot to remove the
dpm($query->__toString())call in line 143. :/ Sorry about that.Comment #32
sebastian.haas commentedJust for the sake of completeness: I've done a patch for TEI which allows to trigger an index rebuild. Otherwise
{taxonomy_entity_index}is only getting updated if you update an entity itself, so it is useful for tac testing purposes to do a re-index of TEI. The admin page can be accessed viaadmin/config/system/taxonomy_entity_indexSee also #1207794: Provide administration form to execute reindexing batch
Comment #33
xjmExcellent! I'll do a code review and some testing when I get the chance. If everything looks good, we can open a project for it.
We'll want to implement a
hook_menu()and move the config toadmin/config/people(per http://drupal.org/node/549094#config-people), and probably as a sub-tab under TAC's config. I've been meaning to add additional tabs to TAC's config for awhile anyway, though, so I'll work that issue out then.Comment #34
sebastian.haas commentedI'm not sure if you got my point, the
admin/config/system/taxonomy_entity_indexstuff is forTaxonomy Entity Indexonly,Taxonomy Access Unpublishedhas no admin ui on it's own, just an additional permission which is set viahook_permission()so I don't think that a re-index command which is only TEI related should be placed in a sub-tab of TAC.I took a look into http://drupal.org/node/549094#config-people and found it most suitable to place it into
admin/config/system. However, it's just TEI stuff so this is not in our backyard.Comment #35
xjmAh, I misunderstood. I see now. Up to davereid, then.
Comment #36
sebastian.haas commentedHm. Those language barriers... :( I think you might want to review and fix my documentation and
hook_help()text as well.Comment #37
xjmTa-da!
http://drupal.org/project/taxonomy_access_unpublished
http://drupal.org/user/1058828/track/code
I made a few changes:
hook_help()a little..installfile, nonexistent configuration path, etc.).I also made a TAC commit to support caching role lists per permission.
So far, the query alter seems to be working nicely. I tested it for anonymous and for a custom role. There's one outstanding issue (no node access update on permission change) but we can open that issue against the new project!
Comment #39
shaundychkoI've been using the module grants module http://drupal.org/project/module_grants to deal with node grants on unpublished content. I've tested it with TAC on unpublished content on D6.
Comment #40
xjm#39: This issue was specific to D7, which completely changed the interactions between taxonomy, unpublished content, and node access.
Comment #41
csuggs4 commentedInstead of using taxonomy_access_unpublished, why not just remove the conditional in the code snippet in #21? Needing this functionality on a very large multi-site, and worried about the non-trivial overhead from taxonomy_access_unpublished.
Thanks!