Forum OpenACS Development: Re: Customizations
i.e. /www/foo.tcl will automatically override /packages/acs-subsite/www/foo.tcl.
This is only helpful if you know your site map but discussion should begin with this mechanism in mind. Before adding new ones ...
It would be nice to have a dynamic mechanism to augment the static one that already exists but ummm ... I'm not sure like the approach discussed above.
Daveb's talking about a per-instance mechanism. That also exists today, but only if you know the instance name, which is clunky. However ... the proposed mechanism is also clunky, no?
As mentioned before, I need customizations for package key, for *ALL* instances of a package. I do agree that the whole idea of subsites which came afterwards does not make any sense in this light and should be dumped.
However, I'd rather build on the existing facility which searches an existing directory structure than add a second facility that looks for individual files buried in the package with magic suffixes.
The general solution should be obvious, one I've mentioned many times in other contexts, that packages should be first-class objects (i.e. there should be a package type, and packages subtyped from the package type). Integrating packages into the object scheme would mean that, for instance, you could derive malte-forums from forums, the RP could search malte-forums/www/* and if a file's not found there, go up the type tree until the template's found.
That, in my book, would count as a generalization of both the package scheme and the existing RP scheme.
Now, that's a dream that ain't coming true soon, but can we come up with a clunky kludge that's more inline with a "real" solution to package customization than using magic filename suffixes known to the RP?
Even something like Or "
Is there a way to prevent us from having to make apm_package_types objects?
a) Add a supertype to the table
b) Work with package_ids, forcing the supertype package to be mounted at least once.
Both do not appeal to me but maybe someone else has some more ideas on that.
What would be involved in making apm_package_types objects? I remember there was a document somewhere on how to make your package use acs_objects, but I forgot where it is. Anyone? And is it that much work that we should shy away from it?
Here are some ideas:
- Create an object_type package_type which uses the apm_package_types extended table
- add a package_type_id which references acs_objects
- drop the PK constraint on package_key, just make it unique and not null
- create objects for all package_types of the object_type "package_type"
- We do not need to change any existing select scripts as we are adding a column, not taking one away. Or am I missing something here ?
- We need to change any script that inserts into apm_package_types, which means to rewrite the function apm_package_type__create_type. And that should be it.
I would think about the RP later, but what are the reasons that speak against making package_types acs_objects ?
Of course, each site would appear as a separate website with custom look.
What a nightmare it would be to churn through all this for slight differences, or merely to avoid security issues. But what about custom pages, new pages for additional functionality?
Anyway, the requirements and my own laziness lead to the development of a single set of tables for all sites, a single instance of ACS4, and an administrative interface which allowed for the instant creation of a new service at the data model level.
Certain things setup in advance greatly help with customization, but the biggest are:
* design for customization
* independent customization code for data model
* complete separation of data from presentation code
* customization aware request processor.
(Shorter version: existence, knowledge and application of tools for Model-View-Controller pattern)
(Even shorter version: integrated separation)
Basically this all boils down to the fact that customization is not an easy add-on. Also inherent in customization is that it is nearly impossible to know in advance what is going to be customized. If customization could be handled by a simple handful of package parameters, it would fall under the heading of configuration, that is, what is allowed is completely defined in advance by the package writer. If this is offered up as customization, developers will quickly argue for new parameters to take into account their changes.
Customization here is...anytime you change something in acs-core and do not want to commit it back.
This is essentially a fork and is already fully supported. This type of customization could be characterized as changes which were not planned for and which nobody wants in the core package.
Instead of asking for changes to support your specific proposed method of customization, why not first change your own request processor and see how well it works for you?
The rp is already complicated and this feature would probably need some examples to show how it works, how it should be used and when. But the proposal appears to require replacing any file which needs any change with a new slightly different file. But for some reason you wish to retain the option of switching back to the original after an update and manual compare/diff. I wonder how the rp will figure out how to ignore the custom files, or which ones to ignore, since an adp and tcl could be changed. Best to not speculate until there is something working and the process can be tested as a whole.
Because I try to collect feedback from the community before I head in any specific direction, especially when it comes down to coding changes into core. And as you can see from the discussion it sparked, my "implementation" would not have been one generally acceptable.
In the past the change I thought off would work when you wanted to change the login screen for users in acs-subsite/lib/login.adp. I managed to make the location of this file a parameter in 5.4 and now you can store that file in a custom package. I did it this way because none of my clients wants the default login.adp, therefore general usefulness is implied.
But what if a client has changed /acs-admin/www/admin/become.tcl to make an additional permission check for special sysadmin privs which they have in their custom application. None of my other clients wants this. It is not generally useful in OpenACS (I'd assume), so the only options at the moment I have is:
a) Make the location a parameter (yet another one?)
b) Write a callback so others can make additional checks if the want to
c) Rewrite their whole handling of permission checks for sysadmins to just use ACS permissions (they would not pay for that)
d) Fork and always remember there is a change in that file when merging new versions from OpenACS
e) Write /www/acs-admin/admin/become.tcl
a-c) Do not make sense.
d) Is something I would like to avoid and be it for the reason that the client could by accident say "update from repository" and overwrite the change.
Doing d) has the benefit that, when a new version comes out and you use a clever merging tool then chances are that you will not run into any problems and still retain your custom changes. At least for a minor change like this. But what if your whole page has changed? Then it might be better to have a custom version of the file and just look at the changes in the OpenACS version and modify if needed manually.
e) Works beautifully (thanks Don for reminding me about that), but only in packages that you mount *once* (otherwise you would have to do it for every mountpoint).
I have seen client installations where a custom package was used and they included the OpenACS functionality. That works as well, but provides a lot of code and makes code maintenance more difficult (as you need to copy files which are not really needed as well, just to make the custom package provide the minimal functionality needed). At least I initially got confused which package is used and mounted when working on that site.
So the idea of Don's appeals to me most at the moment and if there is the time I will probably investigate it a little bit more. For the time being and my immediate needs I am fine with option e), though I would like to come up with a general plan (best practice) on how to do these kinds of customizations / forks you name it.