Moodle
  1. Moodle
  2. MDL-44078

Proposal: API standard in Moodle that uses autoloading (hooks)

    Details

    • Type: Improvement Improvement
    • Status: Open
    • Priority: Minor Minor
    • Resolution: Unresolved
    • Affects Version/s: 2.6.1
    • Fix Version/s: None
    • Component/s: Policy
    • Labels:
    • Affected Branches:
      MOODLE_26_STABLE

      Description

      At the moment Moodle has plenty of little APIs (consisting of one-two functions each) that require plugins to define PLUGINNAME_CALLBACKNAME() functions in their lib.php files.

      Examples:

      • xxx_print_recent_activity
      • xxx_get_recent_mod_activity
      • xxx_reset_course_form_definition
      • xxx_comment_display
      • xxx_grade_item_update
      • xxx_add_istance_hook
      • xxx_restore_group_member
      • xxx_restore_group_assignment
      • xxx_delete_instance
      • xxx_delete_course
      • xxx_supports
        ... (and so on, just grep by "component_callback" or "function_exists" )

      There are several problems with this approach:

      • bad documentation, hard to know about all various existing callbacks
      • easy to confuse the arguments because there is no interface
      • necessary to include all lib.php files (which are sometimes huge) to find handful of plugins implementing functions - SLOW!
      • limiting implementation to one plugin type because otherwise it's too expensive to look for callbacks

      Suggested approach that was discussed on backend meetings, especially with Petr Skoda is to use hooks and class autoloading.

      There is no goal to convert all existing APIs into the new format ASAP but will be nice to gradually do it, slowly deprecating old-style callbacks.

      There are at least two issues that would benefit from the agreement on standard:

      • MDL-43742 converting recent activity callbacks (atm we need to implement two very similar callbacks in each module)
      • MDL-24359 extending course reset callbacks to other plugin types (i.e. blocks)

      Forum post: https://moodle.org/mod/forum/discuss.php?d=254508

        Gliffy Diagrams

          Issue Links

            Activity

            Hide
            Marina Glancy added a comment -

            Proposal for specification: http://docs.moodle.org/dev/Hooks_spec

            Show
            Marina Glancy added a comment - Proposal for specification: http://docs.moodle.org/dev/Hooks_spec
            Hide
            Petr Skoda added a comment -

            here is my little demo of the code (totally untested) https://github.com/skodak/moodle/commits/wip_MDL-44078_m27_hooks

            Show
            Petr Skoda added a comment - here is my little demo of the code (totally untested) https://github.com/skodak/moodle/commits/wip_MDL-44078_m27_hooks
            Hide
            Martin Dougiamas added a comment -

            It's a nice idea for a new system but also quite low priority IMO

            Show
            Martin Dougiamas added a comment - It's a nice idea for a new system but also quite low priority IMO
            Hide
            Tim Hunt added a comment -

            There is no point doing this unless we actually clean up all the old ways of doing things. Your complaint seems to be that there are many different ways to do things in Moodle, and you plan to make it worse by adding another way.

            I do not see the need. In the past we have succeeded in making all add-ons in Moodle more consistent without major changes. E.g. all plugins use db folder in the same way. All plugins use settings.php. Let us continue that, and not add a new way of doing things that is applied inconsistently.

            Show
            Tim Hunt added a comment - There is no point doing this unless we actually clean up all the old ways of doing things. Your complaint seems to be that there are many different ways to do things in Moodle, and you plan to make it worse by adding another way. I do not see the need. In the past we have succeeded in making all add-ons in Moodle more consistent without major changes. E.g. all plugins use db folder in the same way. All plugins use settings.php. Let us continue that, and not add a new way of doing things that is applied inconsistently.
            Hide
            Damyon Wiese added a comment -

            That proposal seems a bit messy to me.

            I would prefer something tied to plugininfo.

            It is more natural to say a plugin supports an API which means it must implement ALL of the multiple hooks to match that API. The best way I can imagine is for plugininfo to implement an interface.

            Show
            Damyon Wiese added a comment - That proposal seems a bit messy to me. I would prefer something tied to plugininfo. It is more natural to say a plugin supports an API which means it must implement ALL of the multiple hooks to match that API. The best way I can imagine is for plugininfo to implement an interface.
            Hide
            Damyon Wiese added a comment -

            Actually the hooks thing could work with using an interface for an API - ie - you define a handler for a hook and it must extend an abstract class/interface.

            Show
            Damyon Wiese added a comment - Actually the hooks thing could work with using an interface for an API - ie - you define a handler for a hook and it must extend an abstract class/interface.
            Hide
            Phil Lello added a comment -

            I quite like the hooks proposal, however I'd be tempted to add a weight parameter to tweak execution order of a hook relative to other hooks (ideally some core functionality would migrate to hooks to support this). I'd also be tempted to have a plugin register callbacks via install.php/upgrade.php, although I suspect that was previously discussed for the events API.

            Show
            Phil Lello added a comment - I quite like the hooks proposal, however I'd be tempted to add a weight parameter to tweak execution order of a hook relative to other hooks (ideally some core functionality would migrate to hooks to support this). I'd also be tempted to have a plugin register callbacks via install.php/upgrade.php, although I suspect that was previously discussed for the events API.
            Hide
            Marina Glancy added a comment -

            Hi Phil, thanks. The 'priority' property can be set in observer, as it does in http://docs.moodle.org/dev/Event_2#Event_observers
            (while looking for a reference I noticed that I put the wrong link to Events API in the hooks document, correcting now)

            Show
            Marina Glancy added a comment - Hi Phil, thanks. The 'priority' property can be set in observer, as it does in http://docs.moodle.org/dev/Event_2#Event_observers (while looking for a reference I noticed that I put the wrong link to Events API in the hooks document, correcting now)
            Hide
            Sam Marshall added a comment -

            I like this proposal & have voted for it. It, or something like it, would make it possible to tidy up a current hardcoded hack in the new conditional availability stuff.

            Show
            Sam Marshall added a comment - I like this proposal & have voted for it. It, or something like it, would make it possible to tidy up a current hardcoded hack in the new conditional availability stuff.
            Hide
            Simon Coggins added a comment -

            I think this would be extremely helpful for us at Totara (or anyone wanting to do extensive customisation of Moodle) to allow us to extend Moodle without having to hack core files.

            Anything which would make the process of merging new versions easier is likely to benefit Moodle customers as it makes it easier for clients with customised sites to stay up to date with recent releases (often the work of merging new versions into a customised site is what puts people off upgrading).

            One example of the kind of uses we would have are, for example, when we want to add additional fields to the course editing page we need to customise core code:

            https://github.com/moodlehq/totara/blob/t2-release-2.5/course/edit_form.php#L379
            https://github.com/moodlehq/totara/blob/t2-release-2.5/course/edit_form.php#L428
            https://github.com/moodlehq/totara/blob/t2-release-2.5/course/edit_form.php#L468

            There are many, many other places like this where we have to include a library and insert a function call - it would be really great to have a standard way to do this.

            Show
            Simon Coggins added a comment - I think this would be extremely helpful for us at Totara (or anyone wanting to do extensive customisation of Moodle) to allow us to extend Moodle without having to hack core files. Anything which would make the process of merging new versions easier is likely to benefit Moodle customers as it makes it easier for clients with customised sites to stay up to date with recent releases (often the work of merging new versions into a customised site is what puts people off upgrading). One example of the kind of uses we would have are, for example, when we want to add additional fields to the course editing page we need to customise core code: https://github.com/moodlehq/totara/blob/t2-release-2.5/course/edit_form.php#L379 https://github.com/moodlehq/totara/blob/t2-release-2.5/course/edit_form.php#L428 https://github.com/moodlehq/totara/blob/t2-release-2.5/course/edit_form.php#L468 There are many, many other places like this where we have to include a library and insert a function call - it would be really great to have a standard way to do this.
            Hide
            Martin Dougiamas added a comment -

            It's useful for open source code to be openly available, eh?

            Show
            Martin Dougiamas added a comment - It's useful for open source code to be openly available, eh?
            Hide
            Simon Coggins added a comment -

            Yeah very handy, thanks Martin

            Show
            Simon Coggins added a comment - Yeah very handy, thanks Martin
            Hide
            David Mudrak added a comment -

            I did not spend enough time on thinking about this to comment on particular implementation details (such as the name of the "create" method etc). But conceptually, I vote +1 for this or something similar to this.

            I can confirm that, from a module's developer point of view, the current way of lib.php callbacks got out of control. We don't know or have a full list of all supported (or even required!) callbacks. One example is MDL-38210 where it turned out that after all the years of Workshop 2.x being in production, it is still missing some callbacks like that. And I remember I paid extra attention to collect them all when I was writing the Workshop lib. Attempting to maintain the list of these callbacks (little apies) in places like NEWMODULE.zip is unmaintainable (I tried, it never ends and does not really help for existing plugins).

            Also, the fact we have to load lib.php from all installed plugins in almost all requests, just smells.

            So, on behalf of all those great people who spend their free time on contributing to Moodle plugins, please :Make it in a way that the plugin developer has easy access of all required and supported APIs - and is informed if the required callback implementation is missing.

            Show
            David Mudrak added a comment - I did not spend enough time on thinking about this to comment on particular implementation details (such as the name of the "create" method etc). But conceptually, I vote +1 for this or something similar to this. I can confirm that, from a module's developer point of view, the current way of lib.php callbacks got out of control. We don't know or have a full list of all supported (or even required!) callbacks. One example is MDL-38210 where it turned out that after all the years of Workshop 2.x being in production, it is still missing some callbacks like that. And I remember I paid extra attention to collect them all when I was writing the Workshop lib. Attempting to maintain the list of these callbacks (little apies) in places like NEWMODULE.zip is unmaintainable (I tried, it never ends and does not really help for existing plugins). Also, the fact we have to load lib.php from all installed plugins in almost all requests, just smells. So, on behalf of all those great people who spend their free time on contributing to Moodle plugins, please :Make it in a way that the plugin developer has easy access of all required and supported APIs - and is informed if the required callback implementation is missing.
            Hide
            Marina Glancy added a comment -

            ok, I guess everybody agrees to close this issue as "Won't fix".

            Let's introduce 1001st and 1002nd callbacks in moodle in MDL-24359 and MDL-40457 and include all plugins on each page in order to check if they implement callbacks. Modern computers are too fast to care about performance. Developers are smart enough to read millions of code lines to know which callback to implement.

            Thanks to everybody who supported this idea but unfortunately it is not happenning.

            Show
            Marina Glancy added a comment - ok, I guess everybody agrees to close this issue as "Won't fix". Let's introduce 1001st and 1002nd callbacks in moodle in MDL-24359 and MDL-40457 and include all plugins on each page in order to check if they implement callbacks. Modern computers are too fast to care about performance. Developers are smart enough to read millions of code lines to know which callback to implement. Thanks to everybody who supported this idea but unfortunately it is not happenning.
            Hide
            Marina Glancy added a comment - - edited

            lol, just as I wrote it another issue was reported - MDL-44678. Well, course reset now has to include lib.php from all plugins of 3 plugin types now (module, block and plagiarism)

            Show
            Marina Glancy added a comment - - edited lol, just as I wrote it another issue was reported - MDL-44678 . Well, course reset now has to include lib.php from all plugins of 3 plugin types now (module, block and plagiarism)
            Hide
            Ray Morris added a comment -

            "everybody agrees to close this issue as "Won't fix"."

            Tabulating the comments above, I count 7 yay and 2 nay. Did "everybody" agree on some other forum?
            I'm with David Mudrak - I haven't analyzed the proposal in detail, but I agree that as Moodle grows the existing approaced is being stretched. Something similar to this proposal would increase the modularity of Moodle.

            However, I also see Tim's point, also made by Randall Munroe https://xkcd.com/927/
            Considering Damyon's comment, is it possible to improve this proposal to the point where we'd definitely want it to be the new standard Moodle way, and therefore plan to replace API using lib.php over time?

            Show
            Ray Morris added a comment - "everybody agrees to close this issue as "Won't fix"." Tabulating the comments above, I count 7 yay and 2 nay. Did "everybody" agree on some other forum? I'm with David Mudrak - I haven't analyzed the proposal in detail, but I agree that as Moodle grows the existing approaced is being stretched. Something similar to this proposal would increase the modularity of Moodle. However, I also see Tim's point, also made by Randall Munroe https://xkcd.com/927/ Considering Damyon's comment, is it possible to improve this proposal to the point where we'd definitely want it to be the new standard Moodle way, and therefore plan to replace API using lib.php over time?
            Hide
            Ray Morris added a comment - - edited

            After having read over the proposal with some care, I like it generally. It reminds me of the Apache hook based module API, which has worked very well for many years.

            I wouldn't argue with Damyon that perhaps they should implement an interface (http://www.php.net/manual/en/language.oop5.interfaces.php) rather than hooking single function. It may be reasonable to think that a plugin which hooks send_query() might be required to hook get_results(). However, hooking a function is a little different than implementing the functionality. The fact that the current system (and the Apache system) effectively hook individual functions shows that doing that works fine too.

            Show
            Ray Morris added a comment - - edited After having read over the proposal with some care, I like it generally. It reminds me of the Apache hook based module API, which has worked very well for many years. I wouldn't argue with Damyon that perhaps they should implement an interface ( http://www.php.net/manual/en/language.oop5.interfaces.php ) rather than hooking single function. It may be reasonable to think that a plugin which hooks send_query() might be required to hook get_results(). However, hooking a function is a little different than implementing the functionality. The fact that the current system (and the Apache system) effectively hook individual functions shows that doing that works fine too.
            Hide
            Martin Dougiamas added a comment -

            Eh? I think most people think this is a great idea, Marina. It just needs some cooking and a considered approach to rollout.

            Show
            Martin Dougiamas added a comment - Eh? I think most people think this is a great idea, Marina. It just needs some cooking and a considered approach to rollout.
            Hide
            Damyon Wiese added a comment -

            And to clarify my comment - I am not against changing the way we implement APIs - the current lib.php approach has many problems and I had exactly the same experience as David when writing the new mod_assign.

            That is why I favour an interface based approach - which is not what is proposed here - and not covered by Petrs patch.

            I would rather a plugin provides a handler for an API and that handler is required to be a subclass that implements an interface (or extends an abstract class - no difference). That is the only way you can be sure that a plugin that implements grading contains all the required callbacks to properly implement grading.

            IMO this hooks patch is too weak and is not much better than the lib.php approach (it will perform better - but that's not my main concern).

            Show
            Damyon Wiese added a comment - And to clarify my comment - I am not against changing the way we implement APIs - the current lib.php approach has many problems and I had exactly the same experience as David when writing the new mod_assign. That is why I favour an interface based approach - which is not what is proposed here - and not covered by Petrs patch. I would rather a plugin provides a handler for an API and that handler is required to be a subclass that implements an interface (or extends an abstract class - no difference). That is the only way you can be sure that a plugin that implements grading contains all the required callbacks to properly implement grading. IMO this hooks patch is too weak and is not much better than the lib.php approach (it will perform better - but that's not my main concern).
            Hide
            Petr Skoda added a comment -

            Interfaces are definitely not a solution for general hacking of core functionality from arbitrary plugin, that is a separate topic. Interfaces may get pretty ugly during upgrades because the mandate all plugins to implement them otherwise you get fatal error. In any case we cannot load classes from all plugins in the system and start asking them if they implement this or that interface.

            So yes, interfaces and abstract classes are good for activity modules, but we cannot use them for general hacks, sorry.

            Show
            Petr Skoda added a comment - Interfaces are definitely not a solution for general hacking of core functionality from arbitrary plugin, that is a separate topic. Interfaces may get pretty ugly during upgrades because the mandate all plugins to implement them otherwise you get fatal error. In any case we cannot load classes from all plugins in the system and start asking them if they implement this or that interface. So yes, interfaces and abstract classes are good for activity modules, but we cannot use them for general hacks, sorry.
            Hide
            Eloy Lafuente (stronk7) added a comment -

            Just to state that I'd love to see organized (explicitly defined, described and used) hooks landing and getting the baton over current callbacks. Surely in a similar way to events. Although the trickiest part will be to define which information are they able to handle/modify and also, at which level (example: a hook(s) for a given form, or a hook(s) for all forms).

            In the other side, I think this only can be considered together with the adaptation of a lot of current callbacks to use the new system, breaking everything the minimum number of times.

            About when an imminent 2.7 LTS is a good moment for that, or which are the policies that will follow that LTS (try keep things unmodified or freedom to break), I still don't know about them, so I'm not able to recommend a good moment for this to land, just now it does not seem to be the best moment.

            Ciao

            Show
            Eloy Lafuente (stronk7) added a comment - Just to state that I'd love to see organized (explicitly defined, described and used) hooks landing and getting the baton over current callbacks. Surely in a similar way to events. Although the trickiest part will be to define which information are they able to handle/modify and also, at which level (example: a hook(s) for a given form, or a hook(s) for all forms). In the other side, I think this only can be considered together with the adaptation of a lot of current callbacks to use the new system, breaking everything the minimum number of times. About when an imminent 2.7 LTS is a good moment for that, or which are the policies that will follow that LTS (try keep things unmodified or freedom to break), I still don't know about them, so I'm not able to recommend a good moment for this to land, just now it does not seem to be the best moment. Ciao
            Hide
            Marina Glancy added a comment -

            Well, this proposal is around since April 2013. Since then it's always "not a good time now" and "not a high priority" and so on. For me it only means that it's not happening.

            My initial idea was also interface but I tend to agree with Petr now that having hook as a class and callback as a method is faster and easier for plugin developers.

            Show
            Marina Glancy added a comment - Well, this proposal is around since April 2013. Since then it's always "not a good time now" and "not a high priority" and so on. For me it only means that it's not happening. My initial idea was also interface but I tend to agree with Petr now that having hook as a class and callback as a method is faster and easier for plugin developers.
            Hide
            Martin Dougiamas added a comment -

            Personally I think it's a requirement of a big API change like this that we DO roll it out all at once and make the change fully and completely. With backward compatibility for 3rd party plugins.

            That's why I see this is as probably a huge decision, and we need more data (how much work this is, how much faster it will be, how the interfaces will be for developers, what the migration looks like) and more consensus from lots of developers.

            Show
            Martin Dougiamas added a comment - Personally I think it's a requirement of a big API change like this that we DO roll it out all at once and make the change fully and completely. With backward compatibility for 3rd party plugins. That's why I see this is as probably a huge decision, and we need more data (how much work this is, how much faster it will be, how the interfaces will be for developers, what the migration looks like) and more consensus from lots of developers.
            Hide
            Damyon Wiese added a comment -

            faster and easier for plugin hook developers

            and will lead to the same situation we have now that the complete list of available hooks is not listed/documented anywhere.

            Show
            Damyon Wiese added a comment - faster and easier for plugin hook developers and will lead to the same situation we have now that the complete list of available hooks is not listed/documented anywhere.
            Hide
            Marina Glancy added a comment -

            no, hook as class is more difficult for hook developer and easier for plugin developer who interacts with this hook because plugin developer does not need to define a class and all methods in it, he just registers one function with one argument.

            Show
            Marina Glancy added a comment - no, hook as class is more difficult for hook developer and easier for plugin developer who interacts with this hook because plugin developer does not need to define a class and all methods in it, he just registers one function with one argument.
            Hide
            Damyon Wiese added a comment -

            I still disagree - but I won't keep harping on - the specific example listed in the dev docs shows why it would be better to use an interface/api approach rather than lots of once off functions. This is because you never want to just add fields to a form - you want to add fields, and then have custom validation for them, and save the submitted data somewhere. So that would be 3 hooks required to extend a form - they are all really required (validation could be optional) - but 3 having separate hooks for the form does not link them together in any meaningful way. It's really the same as a list of functions in lib.php.

            Show
            Damyon Wiese added a comment - I still disagree - but I won't keep harping on - the specific example listed in the dev docs shows why it would be better to use an interface/api approach rather than lots of once off functions. This is because you never want to just add fields to a form - you want to add fields, and then have custom validation for them, and save the submitted data somewhere. So that would be 3 hooks required to extend a form - they are all really required (validation could be optional) - but 3 having separate hooks for the form does not link them together in any meaningful way. It's really the same as a list of functions in lib.php.
            Hide
            Phil Lello added a comment -

            OK, how about we have the following:

            (at core install/upgrade time) : register_hook_provider("hookable-class", "hookable-function", "description");

            (at plugin install/upgrade time) : register_hook_client("hook-client-class", "hook-client-function", "description");

            That way we can have a status page listing all available hooks and all hook clients. It would be useful to have a "rebuild" option on this page to re-run register_hook_provider/register_hook_client code while new ones are developed.

            I haven't thought through the exact syntax, so the signatures are probably wrong, but hopefully the idea is clear enough

            Show
            Phil Lello added a comment - OK, how about we have the following: (at core install/upgrade time) : register_hook_provider("hookable-class", "hookable-function", "description"); (at plugin install/upgrade time) : register_hook_client("hook-client-class", "hook-client-function", "description"); That way we can have a status page listing all available hooks and all hook clients. It would be useful to have a "rebuild" option on this page to re-run register_hook_provider/register_hook_client code while new ones are developed. I haven't thought through the exact syntax, so the signatures are probably wrong, but hopefully the idea is clear enough
            Hide
            Marina Glancy added a comment - - edited

            2Damyon:

            this is still possible with one hook:

            class block_myblock_hook_callbacks {
                public static function courseresetform(\core_course\hook\courseresetform $courseresetformhook) {
                    $courseresetformhook->mform->addElement('checkbox', 'Reset contents of block Myblock');
                    $courseresetformhook->register_validation_function('block_myblock_hook_callbacks::validate');
                    $courseresetformhook->register_submit_function('block_myblock_hook_callbacks::submit');
                }
                public static function validate($mform) {}
                public static function submit($data) {}
            }
            

            maybe not very attractive in this particular case but most of existing callbacks just ask to return some values

            Show
            Marina Glancy added a comment - - edited 2Damyon: this is still possible with one hook: class block_myblock_hook_callbacks { public static function courseresetform(\core_course\hook\courseresetform $courseresetformhook) { $courseresetformhook->mform->addElement('checkbox', 'Reset contents of block Myblock'); $courseresetformhook->register_validation_function('block_myblock_hook_callbacks::validate'); $courseresetformhook->register_submit_function('block_myblock_hook_callbacks::submit'); } public static function validate($mform) {} public static function submit($data) {} } maybe not very attractive in this particular case but most of existing callbacks just ask to return some values
            Hide
            Marina Glancy added a comment -

            2Phil:
            what are advantages of this approach comparing to suggested way http://docs.moodle.org/dev/Hooks_spec ?

            Show
            Marina Glancy added a comment - 2Phil: what are advantages of this approach comparing to suggested way http://docs.moodle.org/dev/Hooks_spec ?
            Hide
            Damyon Wiese added a comment -

            Something like that would be fine Marina - and even better if the code defining the hooks could make some callbacks required, and some optional.

            Show
            Damyon Wiese added a comment - Something like that would be fine Marina - and even better if the code defining the hooks could make some callbacks required, and some optional.
            Hide
            Marina Glancy added a comment -

            Any validation is up to hook developer. Also it might be a good practice to enclose invoking of plugin functions into try/catch. In this case some hacky 3rd party plugin can't break the page completely. Which btw can happen in current moodle callbacks

            Show
            Marina Glancy added a comment - Any validation is up to hook developer. Also it might be a good practice to enclose invoking of plugin functions into try/catch. In this case some hacky 3rd party plugin can't break the page completely. Which btw can happen in current moodle callbacks
            Hide
            Eloy Lafuente (stronk7) added a comment -

            I'd love to see organized (explicitly defined, described and used)...
            — Eloy, some comments above.

            I think the proposed spec is fair enough with that:

            1) all hooks are self-documented (coz all them are using @category and level 2 namespace "hook")
            2) all uses are well defined (coz require db/xxxx.php describing them). Not sure if "hooks.php" is the name for them, and how strictly they should be normalized, as far as they are going to call really heterogeneous code, but that's another story.

            Show
            Eloy Lafuente (stronk7) added a comment - I'd love to see organized (explicitly defined, described and used)... — Eloy, some comments above. I think the proposed spec is fair enough with that: 1) all hooks are self-documented (coz all them are using @category and level 2 namespace "hook") 2) all uses are well defined (coz require db/xxxx.php describing them). Not sure if "hooks.php" is the name for them, and how strictly they should be normalized, as far as they are going to call really heterogeneous code, but that's another story.
            Hide
            Marina Glancy added a comment - - edited

            Upon Martin's request, here is the branch that shows all existing callbacks in Moodle at the moment (more appear in each integration cycle):
            https://github.com/marinaglancy/moodle/compare/x-int-master...wip-MDL-44078-master-hooks

            And just plain list of non-deprecated callbacks:

            COMPONENT_pluginfile
            FULLPLUGINNAME_add_instance_hook
            FULLPLUGINNAME_allow_group_member_remove
            (FULL)PLUGINNAME_cm_info_dynamic
            (FULL)PLUGINNAME_cm_info_view
            FULLPLUGINNAME_comment_add
            FULLPLUGINNAME_comment_display
            FULLPLUGINNAME_comment_permissions
            FULLPLUGINNAME_comment_template
            FULLPLUGINNAME_comment_url
            FULLPLUGINNAME_comment_validate
            FULLPLUGINNAME_delete_course
            FULLPLUGINNAME_dndupload_handle
            (FULL)PLUGINNAME_dndupload_register
            FULLPLUGINNAME_extend_navigation_course
            FULLPLUGINNAME_extend_navigation_module
            FULLPLUGINNAME_extend_navigation_user
            FULLPLUGINNAME_extend_settings_navigation
            FULLPLUGINNAME_extends_navigation
            FULLPLUGINNAME_extends_settings_navigation
            (FULL)PLUGINNAME_get_file_areas
            (FULL)PLUGINNAME_get_file_info
            FULLPLUGINNAME_get_post_actions
            FULLPLUGINNAME_get_question_bank_search_conditions
            FULLPLUGINNAME_get_types
            FULLPLUGINNAME_get_view_actions
            FULLPLUGINNAME_global_db_replace
            FULLPLUGINNAME_grade_item_update
            FULLPLUGINNAME_grading_areas_list
            FULLPLUGINNAME_page_init
            (FULL)PLUGINNAME_page_type_list
            FULLPLUGINNAME_page_type_list
            FULLPLUGINNAME_params_for_js
            (FULL)PLUGINNAME_pluginfile
            FULLPLUGINNAME_pluginfile
            (FULL)PLUGINNAME_print_overview
            FULLPLUGINNAME_print_recent_activity
            FULLPLUGINNAME_question_list_instances
            (FULL)PLUGINNAME_question_pluginfile
            FULLPLUGINNAME_question_pluginfile
            FULLPLUGINNAME_question_preview_pluginfile
            FULLPLUGINNAME_questions_in_use
            FULLPLUGINNAME_rating_get_item_fields
            FULLPLUGINNAME_rating_permissions
            FULLPLUGINNAME_rating_validate
            FULLPLUGINNAME_refresh_events
            FULLPLUGINNAME_restore_group_member
            FULLPLUGINNAME_restore_role_assignment
            FULLPLUGINNAME_strings_for_js
            (FULL)PLUGINNAME_supports
            FULLPLUGINNAME_supports_logstore
            FULLPLUGINNAME_XXX
            glossary_print_entry_FORMATNAME
            glossary_show_entry_FORMATNAME
            grade_export_PLUGINNAME_settings_definition
            grade_import_PLUGINNAME_settings_definition
            grade_report_PLUGINNAME_profilereport
            grade_report_PLUGINNAME_settings_definition
            PLUGINNAME_delete_course
            PLUGINNAME_delete_instance
            PLUGINNAME_export_contents
            PLUGINNAME_extend_settings_navigation
            PLUGINNAME_extends_navigation
            PLUGINNAME_get_completion_state
            PLUGINNAME_get_coursemodule_info
            PLUGINNAME_get_extra_capabilities
            PLUGINNAME_get_post_actions
            PLUGINNAME_get_recent_mod_activity
            PLUGINNAME_get_types
            PLUGINNAME_get_view_actions
            PLUGINNAME_grade_item_update
            PLUGINNAME_print_overview
            PLUGINNAME_print_recent_activity
            PLUGINNAME_print_recent_mod_activity
            PLUGINNAME_report_extend_navigation
            PLUGINNAME_report_extends_navigation
            PLUGINNAME_reset_course_form_defaults
            PLUGINNAME_reset_course_form_definition
            PLUGINNAME_reset_userdata
            PLUGINNAME_rss_get_feed
            PLUGINNAME_scale_used_anywhere
            PLUGINNAME_supports
            PLUGINNAME_update_grades
            PLUGINNAME_user_complete
            PLUGINNAME_user_outline
            $THEME->csspostprocess
            $THEME->extralesscallback
            $THEME->lessvariablescallback
            xmldb_FULLPLUGINNAME_install_recovery
            xmldb_(FULL)PLUGINNAME_uninstall
            

            where
            FULLPLUGINNAME = mod_workshop, block_course_overview, report_participation
            PLUGINNAME = workshop, course_overview, participation
            (FULL)PLUGINNAME = mod_workshop, workshop, block_course_overview, report_participation

            Show
            Marina Glancy added a comment - - edited Upon Martin's request, here is the branch that shows all existing callbacks in Moodle at the moment (more appear in each integration cycle): https://github.com/marinaglancy/moodle/compare/x-int-master...wip-MDL-44078-master-hooks And just plain list of non-deprecated callbacks: COMPONENT_pluginfile FULLPLUGINNAME_add_instance_hook FULLPLUGINNAME_allow_group_member_remove (FULL)PLUGINNAME_cm_info_dynamic (FULL)PLUGINNAME_cm_info_view FULLPLUGINNAME_comment_add FULLPLUGINNAME_comment_display FULLPLUGINNAME_comment_permissions FULLPLUGINNAME_comment_template FULLPLUGINNAME_comment_url FULLPLUGINNAME_comment_validate FULLPLUGINNAME_delete_course FULLPLUGINNAME_dndupload_handle (FULL)PLUGINNAME_dndupload_register FULLPLUGINNAME_extend_navigation_course FULLPLUGINNAME_extend_navigation_module FULLPLUGINNAME_extend_navigation_user FULLPLUGINNAME_extend_settings_navigation FULLPLUGINNAME_extends_navigation FULLPLUGINNAME_extends_settings_navigation (FULL)PLUGINNAME_get_file_areas (FULL)PLUGINNAME_get_file_info FULLPLUGINNAME_get_post_actions FULLPLUGINNAME_get_question_bank_search_conditions FULLPLUGINNAME_get_types FULLPLUGINNAME_get_view_actions FULLPLUGINNAME_global_db_replace FULLPLUGINNAME_grade_item_update FULLPLUGINNAME_grading_areas_list FULLPLUGINNAME_page_init (FULL)PLUGINNAME_page_type_list FULLPLUGINNAME_page_type_list FULLPLUGINNAME_params_for_js (FULL)PLUGINNAME_pluginfile FULLPLUGINNAME_pluginfile (FULL)PLUGINNAME_print_overview FULLPLUGINNAME_print_recent_activity FULLPLUGINNAME_question_list_instances (FULL)PLUGINNAME_question_pluginfile FULLPLUGINNAME_question_pluginfile FULLPLUGINNAME_question_preview_pluginfile FULLPLUGINNAME_questions_in_use FULLPLUGINNAME_rating_get_item_fields FULLPLUGINNAME_rating_permissions FULLPLUGINNAME_rating_validate FULLPLUGINNAME_refresh_events FULLPLUGINNAME_restore_group_member FULLPLUGINNAME_restore_role_assignment FULLPLUGINNAME_strings_for_js (FULL)PLUGINNAME_supports FULLPLUGINNAME_supports_logstore FULLPLUGINNAME_XXX glossary_print_entry_FORMATNAME glossary_show_entry_FORMATNAME grade_export_PLUGINNAME_settings_definition grade_import_PLUGINNAME_settings_definition grade_report_PLUGINNAME_profilereport grade_report_PLUGINNAME_settings_definition PLUGINNAME_delete_course PLUGINNAME_delete_instance PLUGINNAME_export_contents PLUGINNAME_extend_settings_navigation PLUGINNAME_extends_navigation PLUGINNAME_get_completion_state PLUGINNAME_get_coursemodule_info PLUGINNAME_get_extra_capabilities PLUGINNAME_get_post_actions PLUGINNAME_get_recent_mod_activity PLUGINNAME_get_types PLUGINNAME_get_view_actions PLUGINNAME_grade_item_update PLUGINNAME_print_overview PLUGINNAME_print_recent_activity PLUGINNAME_print_recent_mod_activity PLUGINNAME_report_extend_navigation PLUGINNAME_report_extends_navigation PLUGINNAME_reset_course_form_defaults PLUGINNAME_reset_course_form_definition PLUGINNAME_reset_userdata PLUGINNAME_rss_get_feed PLUGINNAME_scale_used_anywhere PLUGINNAME_supports PLUGINNAME_update_grades PLUGINNAME_user_complete PLUGINNAME_user_outline $THEME->csspostprocess $THEME->extralesscallback $THEME->lessvariablescallback xmldb_FULLPLUGINNAME_install_recovery xmldb_(FULL)PLUGINNAME_uninstall where FULLPLUGINNAME = mod_workshop, block_course_overview, report_participation PLUGINNAME = workshop, course_overview, participation (FULL)PLUGINNAME = mod_workshop, workshop, block_course_overview, report_participation
            Hide
            Martin Dougiamas added a comment -

            Great data, thanks Marina.

            Show
            Martin Dougiamas added a comment - Great data, thanks Marina.
            Hide
            Marina Glancy added a comment -

            just saw issue MDL-40457 (currently in integration), it checks class_exists() rather than function_exists(), this is something I did not grep for in my list. (TODO)

            Show
            Marina Glancy added a comment - just saw issue MDL-40457 (currently in integration), it checks class_exists() rather than function_exists(), this is something I did not grep for in my list. (TODO)
            Hide
            Marina Glancy added a comment -

            hi, just want to comment here about recent activity that may be related to this issue.

            First of all, there was a big discussion about plugin-plugin communication where this proposal was mentioned: https://moodle.org/mod/forum/discuss.php?d=261673
            Second, we have an upcoming meeting to discuss the "correct" way of api-plugins and plugin-plugin communication (last one is still under question).

            Interesting issue that was reported recently: MDL-46207 (Scheduled tasks should consider the enabled state of a plugin). Just noting that almost all existing methods to look for callbacks do not take into account if plugin is enabled or not. Whatever way of api standard we agree on, there should be an option of filtering by plugin availability and hopefully one central core_component method to check the plugin availability.

            Also there is an issue MDL-46155 (Core method to retrieve list of classes), inspired by MDL-40457 (finally integrated this week) and existing report_eventlist. It is work in progress atm and one of the things that is missing is the check if plugin is enabled.

            Show
            Marina Glancy added a comment - hi, just want to comment here about recent activity that may be related to this issue. First of all, there was a big discussion about plugin-plugin communication where this proposal was mentioned: https://moodle.org/mod/forum/discuss.php?d=261673 Second, we have an upcoming meeting to discuss the "correct" way of api-plugins and plugin-plugin communication (last one is still under question). Interesting issue that was reported recently: MDL-46207 (Scheduled tasks should consider the enabled state of a plugin). Just noting that almost all existing methods to look for callbacks do not take into account if plugin is enabled or not. Whatever way of api standard we agree on, there should be an option of filtering by plugin availability and hopefully one central core_component method to check the plugin availability. Also there is an issue MDL-46155 (Core method to retrieve list of classes), inspired by MDL-40457 (finally integrated this week) and existing report_eventlist. It is work in progress atm and one of the things that is missing is the check if plugin is enabled.

              People

              • Votes:
                14 Vote for this issue
                Watchers:
                22 Start watching this issue

                Dates

                • Created:
                  Updated: