PyroCMS v0.9.7.4 - an open-source modular general purpose CMS |
[eluser]Turv[/eluser]
I think i have a possible solution i'm working on now. Will post back shortly.
[eluser]Turv[/eluser]
Okay, Well i hit a stump... I've got a solution that will allow an unlimited sub-page structure so you can have pages such as /parent/primary/secondary/sub-page/ It works by passing an array of URI Segments to the page function, This receives an array such as Code: Array With sub-page being the targetting page for content, I store this slug in a variable, remove it from the array. The last item in the array (Secondary) is then the parent of this page. So i query the database to get the ID (Parent ID) for the Secondary page. If there are more than one result, I perform the final query where i find a row in the database where the slug is 'sub-page' and the parent id is whatever the id of secondary is. This means you can have multiple 'sub-page' slugs. However...The problem i have is that if i have pages where the last parts are identical (unlikley to happen?) it causes problems. Such as, If i have another page such as... Code: Array Then with the last two parts (secondary/sub-page) being the same it fails. What i need is a way to recursively call getIdBySlug passing a new parent slug until i get a reslt with only one row. This is the code i have... Pages Controller, _remap function Change: If a sub page (of any kind) exists then pass on the uri segment array, otherwise just pass the first segment, call page function directly Code: function _remap() Page Controller, Pages function Change: Restored back to the original, No changes needed in this function anymore Pages Model, getBySlug function Code: public function getBySlug($slug = '', $lang = NULL) Pages Model, getIdBySlug function Code: public function getIdBySlug($parent = null, $slug = null) { So basically, what i did in my test installation was create a number of child pages so i had two urls as below /primary/sub-page/sub-sub-page/ /test-page/sub-page/sub-sub-page/ When going to /test-page/sub-page/sub-sub-page/ i received the content for /primary/sub-page/sub-sub-page/ because in my getIdBySlug function, when doing the additional check i return the id as soon as i find a match. What i need to do instead is like a recursive function using the rest of the uri array to....I don't know, have a look see if you can figure anything out. This at the moment...seems to work perfectly for any url as long as there are not two segments of the same name as per the above example
[eluser]ray73864[/eluser]
One thing you could do, is get the entire ancestry for 'sub-sub-page', starting with the parent 'primary' or 'test-page' and working your way through the chain, get the id for 'test-page' then the id for 'sub-page' then for 'sub-sub-page'. Once you have the full ancestry then you will be assured that you have the correct page the person is asking for.
[eluser]Turv[/eluser]
[quote author="ray73864" date="1251209638"]One thing you could do, is get the entire ancestry for 'sub-sub-page', starting with the parent 'primary' or 'test-page' and working your way through the chain, get the id for 'test-page' then the id for 'sub-page' then for 'sub-sub-page'. Once you have the full ancestry then you will be assured that you have the correct page the person is asking for.[/quote] Yeah that's what i was thinking, I mean the above solution works just fine for 99% of scenarious i mean on content pages the likelyhood you are going to have a sub page, and sub sub page of the same value is very unlikely as if you are, chances are it should be a module like product/details. That's why i thought about doing some form of recursive function, I mean i have the array of 'slugs' at hand, I just need to go through each one to verify the correct parent ID, If i can get the correct Parent ID I can perform the query and retreive the correct content and it will work just fine.
[eluser]Phil Sturgeon[/eluser]
Code: exit('where did this code go?! tell me if you see this message [email protected]!'); Ha! Brilliant... Recursive is correct. This needs to loop through all segments in the URL to find the correct child. We cannot simply assume the same child wont exist in two places, as easy as that might make development. Turv, while you work on this if the Language element of the page manager gets in your way please feel free to delete ALL of it, no mercy. That feature is screwed and needs to be disabled anyway.
[eluser]Phil Sturgeon[/eluser]
A little something like this? Code: $last_slug = array_pop($url_segments); Something like this might start us in the right direction. Basically looks to the slug as unique then chases up the tree using self joins, each way checking the slug matches so we should get the right tree even if there are multiple children with matching names. Untested mind. Anyone free to check it out? Update: This is a implementation of the theory shown here.
[eluser]Phil Sturgeon[/eluser]
OK scratch that, I was close but not entirely. The magic query we need to use is this: Quote:SELECT p3.* This will support everything we need from it. It will pick the correct tree and make sure even if there are two "child" or "grandchild" slugs anywhere else it will still take the right path. I have roughed up some code (not tested). Code: // Work out how many segments there are Something like that should do. Sudden inspiration! :lol:
[eluser]Turv[/eluser]
[quote author="Phil Sturgeon" date="1251226630"]OK scratch that, I was close but not entirely. The magic query we need to use is this: Quote:SELECT p3.* This will support everything we need from it. It will pick the correct tree and make sure even if there are two "child" or "grandchild" slugs anywhere else it will still take the right path. I have roughed up some code (not tested). Code: // Work out how many segments there are Something like that should do. Sudden inspiration! :lol:[/quote] Fantastic! Got it working! This is now my getBySlug function Code: public function getBySlug($slug = '', $lang = NULL) There is one problem with this code it seems, and it's the From clause. This is the output query of the above (using my test) Code: SELECT p3.* This produced 10 results apparently, Hence the limit clause. However changing the from clause to this makes it work perfectly. Note: The only difference is the from clause is 'FROM pages as p1' where as CI produces FROM (pages AS p1, pages). Why is it doing that, and can we make it produce what we want? Code: SELECT p3.* Great job bud, I would have never thought about doing that.
[eluser]Phil Sturgeon[/eluser]
Sweet, glad my code was helpful! The problem is that getBySlug() currently just sets up the db clauses then runs through $this->get() to grab the content. This whole model looks bloody disgusting and really needs some cleaning! A few things here. I would take out the AS commands, they are not needed and might screw with things a bit. It is not a LEFT join, as neither side is any more likely to exit. It is closest to being an outter join, but the WHERE clause will destroy it anyway, so leave the 3rd param in the join blank. We should change this model now as there is no longer any need to ever get a page by a slug. It will always be edited, viewed or referenced by an ID or the uri segments. Here is a suggestion of how the model should probably look now. This replaces getById(), getBySlug() and get() with a modified getById() and a renamed function getByURL(). get() is deleted. You might also notice me being picky with your syntax. It is partially me being anal and partially me wanting to keep the CMS using the same sytax all over. camelCase for functions, underscores for variables, allman for structures. Other than that, good work dude! :-)
[eluser]sigork[/eluser]
What is the license of PyroCMS? GNU GPL v3? Creative Commons (by-nc-nd)? ... Thanks. |
Welcome Guest, Not a member yet? Register Sign In |