Hi all,
I've created a copy of the Vector skin. What is the recommended way to register resources (for the resource loader) for a custom skin?
Vector registers the resources in resources/Resources.php
The recommended method for extensions seems to define $wgResourceModules['ext.myExtension'] in the MyExtension.php file
This does not seem to work for styles. I get a blank page when I do this in my skin, and load /load.php?debug=true&lang=en-gb&modules=skins.myskin&only=styles&skin=myskin&* in my browser.
Here is what I tried so far: 1. Don't define anything --> PHP Fatal error: Call to a member function getGroup() on a non-object in includes/OutputPage.php on line 2958
2. define $wgResourceModules['skins.myskin'] in the MySkin.php --> blank page
3. define $wgResourceModules['skins.myskin'] in SkinMySkin (extends SkinTemplate) __construct() function --> blank page
4. call $resourceLoader->register('skins.myskin', ...) from a hook function, defined by $wgHooks['ResourceLoaderRegisterModules'][] in MySkin.php. --> blank page
5. define $wgResourceModules['skins.myskin'] in the MySkin.deps.php --> blank page
6. define 'skins.myskin' in resources/Resources.php --> works fine (but I rather not modify this file)
7. define $wgResourceModules['skins.myskin'] in LocalSettings.php --> works fine (but feels rather hackerish, since I have to manually set $wgStyleDirectory)
Unfortunately, http://www.mediawiki.org/wiki/Manual:Skinning is deprecated, and http://www.mediawiki.org/wiki/ResourceLoader/Migration_guide_(developers) does not mention skins at all.
Apparently, more people struggle with this: http://www.mediawiki.org/wiki/Manual_talk:Skinning/Vector
Any help is kindly appreciated!
Regards, Freek Dijkstra
Freek Dijkstra wrote:
Hi all,
I've created a copy of the Vector skin. What is the recommended way to register resources (for the resource loader) for a custom skin?
Vector registers the resources in resources/Resources.php
The recommended method for extensions seems to define $wgResourceModules['ext.myExtension'] in the MyExtension.php file
This does not seem to work for styles. I get a blank page when I do this in my skin, and load /load.php?debug=true&lang=en-gb&modules=skins.myskin&only=styles&skin=myskin&* in my browser.
It occurs to me that the cause may be that Index.php (the HTML) pages includes MySkin.php, but load.php (the CSS) does not include MySkin.php.
Is this intended behaviour or a bug?
Here is what I tried so far:
- Don't define anything
--> PHP Fatal error: Call to a member function getGroup() on a non-object in includes/OutputPage.php on line 2958
- define $wgResourceModules['skins.myskin'] in the MySkin.php
--> blank page
- define $wgResourceModules['skins.myskin'] in SkinMySkin (extends
SkinTemplate) __construct() function --> blank page
- call $resourceLoader->register('skins.myskin', ...) from a hook
function, defined by $wgHooks['ResourceLoaderRegisterModules'][] in MySkin.php. --> blank page
- define $wgResourceModules['skins.myskin'] in the MySkin.deps.php
--> blank page
- define 'skins.myskin' in resources/Resources.php
--> works fine (but I rather not modify this file)
- define $wgResourceModules['skins.myskin'] in LocalSettings.php
--> works fine (but feels rather hackerish, since I have to manually set $wgStyleDirectory)
Unfortunately, http://www.mediawiki.org/wiki/Manual:Skinning is deprecated, and http://www.mediawiki.org/wiki/ResourceLoader/Migration_guide_(developers) does not mention skins at all.
Apparently, more people struggle with this: http://www.mediawiki.org/wiki/Manual_talk:Skinning/Vector
Any help is kindly appreciated!
Regards, Freek
On Wed, Feb 1, 2012 at 5:51 AM, Freek Dijkstra software@macfreek.nl wrote:
Hi all,
I've created a copy of the Vector skin. What is the recommended way to register resources (for the resource loader) for a custom skin?
Vector registers the resources in resources/Resources.php
This is not really well thought-out at this point, unfortunately :( . I'll file a bug about this, and think about it for a bit later today.
Roan
On Wed, 01 Feb 2012 04:04:50 -0800, Roan Kattouw roan.kattouw@gmail.com wrote:
On Wed, Feb 1, 2012 at 5:51 AM, Freek Dijkstra software@macfreek.nl wrote:
Hi all,
I've created a copy of the Vector skin. What is the recommended way to register resources (for the resource loader) for a custom skin?
Vector registers the resources in resources/Resources.php
This is not really well thought-out at this point, unfortunately :( . I'll file a bug about this, and think about it for a bit later today.
Roan
I haven't been able to release the skinning tutorial I've been working on, but I have a new recommended file layout for non-core skins.
Goes something like this, assuming a skin called "CloneBook": clonebook/clonebook.php clonebook/CloneBook.i18n.php (or maybe clonebook/clonebook.i18n.php?) clonebook/CloneBook.skin.php clonebook/*.{js,css,etc...} (or something like clonebook/styles/*.css or clonebook/css/*.css if you feel like it instead)
You put the $wgValidSkinNames, $wgAutoloadClasses, $wgResourceModules, etc... data inside of the clonebook/clonebook.php file and include it like an extension: require_once("$IP/skins/clonebook/clonebook.php");
This gives you a number of advantages: - You can finally throw your skin into a tarball and distribute it in a way that can simply be extracted - You don't lose the advantage of resources sitting inside of skins/ - You have a good place to define things like resource loader modules - You have a place for i18n, which was sort of missing before - You can also define extension credits for your skin and get attribution
The key reason for putting it inside of skins/ instead of extensions/ is that by putting it inside of skins/ we have the advantage of having a absolute fact saying that "This is a skin", not some complex extension. And that means that we can start making conventions that are based on that fact and start stripping away the requirements to use extension-like code by slowly introducing various bits of auto-loading into future versions of MediaWiki.
For example in a future version of MediaWiki we may suggest replacing require_once calls and have some sort of skin manifest: SkinLoader::registerSkin( 'clonebook' );
clonebook/clonebook.skin.xml <skin> <key>CloneBook</key> <name lang="en">Clone Book</name> <description lang="en">A clone of MonoBook... what else do you need?</description> <author url="//mediawiki.org/wiki/User:Dantman">Daniel Friesen</author> <mwpage>Skin:CloneBook</mwpage><!-- Alternative to url --> <resource-module> <style media="screen">screen.css</style> <style media="print">print.css</style> </resource-module> </skin>
Then you would have your conventional clonebook/<key>.skin.php file and $wgValidSkinNames, $wgAutoLoadClasses, and wgResourceModules would all be implicitly set, your extension credits would be implicitly set, and the name and description of the skin would implicitly be put into i18n. You would only need an i18n file at that point if you actually used custom i18n message keys inside of your skin. Not just to i18n the name of your skin and it's credits description.
On 02/01/2012 07:42 AM, Daniel Friesen wrote:
I haven't been able to release the skinning tutorial I've been working on, but I have a new recommended file layout for non-core skins.
Daniel, please just put up what you have now somewhere, if you can. It's just not scalable or sustainable for you to be a bottleneck here as practically the only person who knows the skins system. Even an unfinished tutorial is better than nothing.
Also, are you already working with Owen Davis & the Wikia folks regarding their skin rewrite proposal?
On 12-02-01 5:11 AM, Sumana Harihareswara wrote:
On 02/01/2012 07:42 AM, Daniel Friesen wrote:
I haven't been able to release the skinning tutorial I've been working on, but I have a new recommended file layout for non-core skins.
Daniel, please just put up what you have now somewhere, if you can. It's just not scalable or sustainable for you to be a bottleneck here as practically the only person who knows the skins system. Even an unfinished tutorial is better than nothing.
I've always had very little spare time to code or do anything substantial, especially with writing. And my employer wanted to get a little publicity out so we could get more clients who wanted us to do MediaWiki Skinning work (Really, being stuck in WordPress is HELL). So I decided to convince my employer to let me spend work hours writing the skinning tutorial and publish it first on a new company blog before putting an editable derivative up in the manual. And unfortunately we've been too busy and chaotic (I got sick) to move on with it. So unfinished or finished I can't hand it out without an ok since I don't have the implicit copyright given I used work hours (and I used what added up to at least a weeks worth of work) to write it.
I sent a message to Greg on the topic. Though he's been busy lately and one of our clients with an upcoming Oprah appearance has been hammering him with calls, even off-hours.
Also, are you already working with Owen Davis & the Wikia folks regarding their skin rewrite proposal?
No one sent me any information about that -- In fact this might be the first I've even heard of it. Though I'd love to see their ideas.
~Daniel Friesen (Dantman, Nadir-Seen-Fire) [http://daniel.friesen.name]
On 02/03/2012 10:33 PM, Daniel Friesen wrote:
On 12-02-01 5:11 AM, Sumana Harihareswara wrote:
On 02/01/2012 07:42 AM, Daniel Friesen wrote:
I haven't been able to release the skinning tutorial I've been working on, but I have a new recommended file layout for non-core skins.
Daniel, please just put up what you have now somewhere, if you can. It's just not scalable or sustainable for you to be a bottleneck here as practically the only person who knows the skins system. Even an unfinished tutorial is better than nothing.
I've always had very little spare time to code or do anything substantial, especially with writing. And my employer wanted to get a little publicity out so we could get more clients who wanted us to do MediaWiki Skinning work (Really, being stuck in WordPress is HELL). So I decided to convince my employer to let me spend work hours writing the skinning tutorial and publish it first on a new company blog before putting an editable derivative up in the manual. And unfortunately we've been too busy and chaotic (I got sick) to move on with it.
Whatever state it's in, if you are too busy to finish it, you can hand it to me and I will finish it. Ask any of the developers I've worked with -- I can interview them relatively fast over IRC and/or the phone and then turn that into usable prose.
Sad to hear you've been sick; hope you feel better soon.
So unfinished or finished I can't hand it out without an ok since I don't have the implicit copyright given I used work hours (and I used what added up to at least a weeks worth of work) to write it.
I sent a message to Greg on the topic. Though he's been busy lately and one of our clients with an upcoming Oprah appearance has been hammering him with calls, even off-hours.
Next time, just work in the open with us from the start and you won't have this problem. Writing rough drafts in a subpage on mediawiki.org == fait accompli. :-)
Every other day, someone comes into #mediawiki asking for help with skins, and we end up pointing them to you. If your boss lets you publish or hand over this tutorial, it will save time by reducing this free customer service obligation! You can tell your boss that. And if he says no, let me know. Maybe we can make sure that every time he looks at Wikipedia, he sees an IP-specific banner ad: A Personal Appeal
From Sumana Harihareswara Of The Wikimedia Foundation. :-)
Also, are you already working with Owen Davis & the Wikia folks regarding their skin rewrite proposal?
No one sent me any information about that -- In fact this might be the first I've even heard of it. Though I'd love to see their ideas.
~Daniel Friesen (Dantman, Nadir-Seen-Fire) [http://daniel.friesen.name]
CC'ing Owen and urging him to talk about it on wikitech-l. Or, Inez, maybe you can tell us?
On Feb 3, 2012, at 7:33 PM, Daniel Friesen wrote:
Also, are you already working with Owen Davis & the Wikia folks regarding their skin rewrite proposal?
No one sent me any information about that -- In fact this might be the first I've even heard of it. Though I'd love to see their ideas.
~Daniel Friesen (Dantman, Nadir-Seen-Fire) [http://daniel.friesen.name]
I haven't had time to respond to this, I've been a bit swamped… Here's a summary...
The approach we took was to make a self contained and modular mini-framework for building skins. It borrows a lot from Symfony. Typically with mediawiki skins, you have a giant skin template file which defines an template object and contains bunch of html, which then calls a bunch of helper functions to build more html. We felt it got pretty unmanageable pretty quickly with our Monaco skin, which takes the same approach. What we did with Oasis was basically reduce it to this:
class OasisTemplate extends QuickTemplate {
echo Module::get('Oasis', 'Index')->render();
// or echo wfRenderModule('Oasis', 'Index');
}
And then define a Data TransferObject + Controller hybrid. All public variables are exported to the template, which reduces the amount of boilerplate PHP syntax to a minimum:
class OasisModule extends Module {
public $foo; public $bar; public $wgGlobalVar; // any global reference is auto-copied to the template
public function executeIndex() { // any function called executeX is "dispatchable", the rest are helpers // controller logic goes here $this->foo = FooService::getSomeFoo(); $this->bar = BarService::getSomeBar(); } }
And the template/view is just a raw php file called Oasis_Index.php :
<div> <div> <?php if (isset($wgGlobalVar)) echo $foo ?> </div> <div> <?= $bar ?> </div> <div> <?= Module::get('Something', 'Index')->render(); ?> <div> <?= wfRenderModule('OtherThing', 'Whatever'); ?> </div>
As long as the names match up, the Module class matches up the controller method and the view template (Index, in this case). Of course, when we got to really building the skin, it got a lot more complicated, and now it's undergone a bit of a transformation into a more formal MVVC framework which obscures the simplicity of the original approach. But that was the idea. We have something like 40+ modules in the skin itself, and who knows how many more in extensions.
The nice thing about this was that doing Module::get("Thing", "Index")->getData() will just give you a raw array of data, which means any controller methods can double as an ajax call (after transforming it to json) or a service class for some other piece of PHP, which is a shortcut we use a lot.
At this point, the Oasis skin has been stretched (ha) far beyond it's initial design and it's holding up… okay, I guess. It's easy for people to find one small section of the code and just work on that, and you can test individual components separately and see the raw data or the raw html for any module directly in the browser, which was the goal. The modules actually got converted to something more like full blown controllers with a dispatcher framework a while ago. You can see the current version of the entry point here:
http://trac.wikia-code.com/browser/wikia/trunk/skins/Oasis.php
And an example of how the modules can get pretty complex, and how you DON'T want that logic in a template:
http://trac.wikia-code.com/browser/wikia/trunk/skins/oasis/modules/LatestAct... http://trac.wikia-code.com/browser/wikia/trunk/skins/oasis/modules/templates...
and an example of the raw data for that exact bit of code on a live wiki:
http://community.wikia.com/wikia.php?controller=LatestActivity&method=In...
and the html without the rest of the skin:
http://community.wikia.com/wikia.php?controller=LatestActivity&method=In...
It's really not MUCH more complicated, and I think the basic concept could be extracted and simplified and open sourced pretty easily. Oasis at this point depends on a LOT of other wikia code, but the design itself doesn't. And it's all one step closer to a more formal web services framework, which is I guess where we are going in the long run…? I'm not sure if this is something anybody else is interested in, but I'm happy to provide more details.
owen@wikia-inc.com
wikitech-l@lists.wikimedia.org