Forum OpenACS Q&A: multirow insert?

Collapse
Posted by David Kuczek on
How can I insert a second multirow in an existing multirow?

For example: I have two mulirows with one column (unique URLs within one multirow)

I want to insert the second multirow right after the first multirow where url_1 = url_2...

Cheers

Collapse
2: Re: multirow insert? (response to 1)
Posted by Brian Fenton on
Hi David,

It would be helpful if you gave an example of what you're trying to achieve.
Are your multirows coming from 2 select statements? If so, maybe you can achieve what you want by having just 1 select statement and using a join. Then use the GROUP tag in your adp .

I can expand on this if I haven't given enough detail.

Brian

Collapse
3: Re: multirow insert? (response to 1)
Posted by David Kuczek on
Hey Brian,

I want to automatically build a left side vertical etp navigation.

So I created a proc called ad_navigation_bar which basically works the same as ad_context_bar, but returns the package_ids of all iterations.

I wanted to start with iteration_0 on etp:get_content_items

etp::get_content_items -package_id "$package_id_0" -result_name "content_items_0"

and go on to the last iteration. This way I would have all needed to components for a navigation. I would just have to put them together correctly and highlight the one that is currently active...

Thanks

Collapse
4: Re: multirow insert? (response to 1)
Posted by Dave Bauer on
You can append to a multirow, but in this case I believe you should write one query that returns all the rows you will need.

Doing the seperate query for each package_id will be inefficient. I believe the results of the get_content_items procedure may be cached, but it still seems like the wrong way to go about it.

Another option would be to allow get_content_items to accept a list of package_ids or have it append to the multirow name that you pass in if the multirow already exists.

Collapse
5: Re: multirow insert? (response to 1)
Posted by Jun Yamog on
I agree with Dave.  One query, I have done something similar with modetp if not the same.  To the one who had a copy please post, I don't have it anymore.

Basically you will need to use the tree_sortkey and tree_* plsql.  Then sort by tree_sortkey.  So the nodes will fall under properly.

Also its possible to it may be a union.  Like getting the root sections.  And then just getting the tree of your current context.  Since some navigation seems to like to have the other nodes collapsed.  Good Luck!

Collapse
6: Re: multirow insert? (response to 1)
Posted by David Kuczek on
I remembered that Robert Locke send me this kinda code some time ago... The best way to get the root_package_id would be to enhance ad_context_bar to also return the package_ids within its list. This way you wouldn't have to perform redundant queries.

How would I have to change the following code? If nobody answers I will just work the code a little (lazy me 😊...

Will I need any kind of modetp code to use this with etp?

#####

set root_item_id [modetp::get_root_item_id [ad_conn package_id]]

db_multirow all_pages all_pages {
    select
        i.item_id,
        tree_level(i.tree_sortkey) - (select tree_level(tree_sortkey)
from
cr_items where item_id = :root_item_id) as item_level,
        null as indent, -- set below
        etp__get_title(i.item_id, r.title) as title,
        etp__get_absolute_url(i.item_id, i.name) as url,
        o.object_type
    from
        cr_items i left join modetp_revisions r on (i.live_revision =
r.revision_id)
        left join cr_modetp_content c on (i.item_id = c.content_id),
        acs_objects o
    where
        i.item_id = o.object_id
        and o.object_type in ('content_item', 'content_folder')
        and (i.name != 'index' or i.item_id = :root_item_id)
        and i.tree_sortkey >= (select tree_sortkey from cr_items where
item_id = :root_item_id)
        and i.tree_sortkey < (select tree_right(tree_sortkey) from
cr_items
where item_id = :root_item_id)
        and (coalesce(c.level, r.level) != 0 or i.item_id =
:root_item_id)
        and (coalesce(c.live_date, r.live_date) is null
            or current_timestamp > coalesce(c.live_date, r.live_date))
        and (coalesce(c.archive_date, r.archive_date) is null
            or current_timestamp < coalesce(c.archive_date,
r.archive_date))
        order by
            i.tree_sortkey
} {
    set indent [string repeat "&nbsp;" [expr $item_level * 4]]
}

Collapse
7: Re: multirow insert? (response to 1)
Posted by David Kuczek on
Jun,

could you help out with that query... I was working on it, but didn't understand all the depth of CR + I am using etp instead of modetp.

The main problems I had was limiting the results to exactly those that etp is actively using.

I eliminated the rows that didn't work with "--" and manually put in my root_item_id so that I can see the results in the db.

You basically order by tree_sortkey and limit it by (among others) "select tree_right(tree_sortkey)". If I do this only the root_item_id is being displayed. If I don't do it the results are too many and the external links are not being shown.

And what did you use the modetp_cr_content table for???

I think that this kind of navigation would really be useful for oacs (marketing 😊...

Cheers

#####

    select
        i.item_id,
        tree_level(i.tree_sortkey) - (select tree_level(tree_sortkey) from cr_items where item_id = 2157) as item_level,
        null as indent, -- set below
        etp__get_title(i.item_id, r.title) as title,
        i.name,
        --etp__get_absolute_url(i.item_id, i.name) as url,
        o.object_type
    from
        cr_items i
          left join cr_revisions r on (i.live_revision = r.revision_id),
          --left join cr_modetp_content c on (i.item_id = c.content_id),
        acs_objects o
    where
        i.item_id = o.object_id
        and o.object_type in ('content_item', 'content_folder')
        and (i.name != 'index' or i.item_id = 2157)
        and i.tree_sortkey >= (select tree_sortkey from cr_items where item_id = 2157)
        --and i.tree_sortkey < (select tree_right(tree_sortkey) from cr_items where item_id = 2157)
        --and (coalesce(c.level, r.level) != 0 or i.item_id = 2157)
        --and (coalesce(c.live_date, r.live_date) is null or current_timestamp > coalesce(c.live_date, r.live_date))
        --and (coalesce(c.archive_date, r.archive_date) is null or current_timestamp < coalesce(c.archive_date, r.archive_date))
        order by
            i.tree_sortkey

Collapse
8: Re: multirow insert? (response to 1)
Posted by Jun Yamog on
Hi David,

I am sorry I am little time right now.  But the basic query is like this.

select                      i.item_id,
                            i.name,
                            i.parent_id,
                            tree_level(i.tree_sortkey) as level,
                            tree_level(p.tree_sortkey) as parent_level,
                    from cr_items i,
                        (select item_id, tree_sortkey from cr_items where item_id = :parent_id) p
                    where
                        and i.tree_sortkey between p.tree_sortkey and tree_right(p.tree_sortkey)
                    order by i.tree_sortkey

That should display a subtree of CR.  Take note that tree_sortkey is not a CR issue.  Its the way oacs was ported in pg.

I think Rob added a table to make the navigation.  When I was working on modetp, I simply had rules and derived the navigation from it.  Rob made a table to explicitly put which items are in navigation or not.