How to create document having a link between them

91 views
Skip to first unread message

Adrien Nicolet

unread,
Dec 12, 2012, 9:47:03 AM12/12/12
to crea...@googlegroups.com
Hi there,


I'm working with createjs, createphp and the CreateBundle on the Symfony CMF Sandbox (http://cmf.liip.ch).

The goal is to build a news list where it is possible to create news with createjs. This is very similar to what has been done for the CMF Website (https://github.com/symfony-cmf/symfony-cmf-website/pull/9). The difference is the way data are organized in the repository (using PHPCR). On the CMF Website, the SimpleCmsBundle is used, and has one single tree node for the content, menu and routes, all under /cms/simple. But with the sandbox, there is a tree for content, one for the routes and one for the menu, under /cms/content, /cms/routes and /cms/menu.

So, in the Sandbox, when we want to create a news, we need to save the news content in the repository (PHPCR), and then the route. The route needs to have a link to the content. It is then needed to wait for the content creation to be able to set the correct relation.

I want to do this as far as possible in the frontend. When a new document is saved successfully, I thought about creating another request to send to the backend, with the subject of the document just created. For that, I guess I need to overwrite the midgardstoragesaved event. I still need to figure out how I can get the subject that comes with the http response of the document creation...


What do you think about this approach? Would you recommand another technique to store two differente entities that still have a link between them?


Thanks for your help!




Adrien (adou600)

David Buchmann

unread,
Dec 13, 2012, 5:02:44 AM12/13/12
to crea...@googlegroups.com, Adrien Nicolet
if this all does not work, we could try to cheat ourselves out of the
problem in this case i think.

we could add a listener that automatically creates a route document on
post-persist of a content document. by looking at the route of the
parent of the document and create a child to that route with the same
name as the document has.

but this feels hacky, and will play hell when creating content any other
way.
and you can't let the user decide the url in some sort of meta data. or
handle multiple routes for multilanguage.

cheers,david
> --
>
>
>

--
Liip AG // Agile Web Development // T +41 26 422 25 11
CH-1700 Fribourg // PGP 0xA581808B // www.liip.ch

Adrien Nicolet

unread,
Dec 14, 2012, 11:51:55 AM12/14/12
to crea...@googlegroups.com, Adrien Nicolet
I was able to get the id of the entity generated in PHPCR:

$('body').bind('midgardstoragesavedentity', function (event, options) {
    console.log('id of the create entity in phpcr: ' + options.entity.id);
});

So now, the idea would be to generate a new "RouteDocument" from here, whith this options.entity.id and to POST it to the backend. Any idea on how to do this in a clean way?

One of the advantages to do it in the frontend is that it let the possibility for the user to choose the route he wants... But otherwise, there would be the solution proposed before by David. 

Adrien Nicolet

unread,
Dec 19, 2012, 11:34:24 AM12/19/12
to crea...@googlegroups.com, Adrien Nicolet
A little situation update for the case. It went forward thanks to Bergie's answers on the IRC. 

I now have the following code:

jQuery(document).ready(function() {
    $('body').bind('midgardstoragesavedentity', function (event, options) {
        
        var routeRequest = {};
        routeRequest["@type"] = "<cmf:CmfRoute>";
        routeRequest["@subject"] = options.entity.id;
        routeRequest["<http://cmf.symfony.com/CmfRoute/Parent>"] = "/cms/routes/en/news";
        //and other parameters...
        
        options.entity.vie.namespaces.add("cmf","http://cmf.symfony.com/");
        options.entity.vie.namespaces.add("route","http://cmf.symfony.com/CmfRoute");
        
        var myEntity = new options.entity.vie.Entity();
        myEntity.set(routeRequest);
        options.entity.vie.entities.add(myEntity);
        
        jQuery('body').midgardStorage('saveRemote', myEntity);
    });
});


But I now get the following backbone error after the last line: Error: A "url" property or function must be specified. I don't get why. I've read that these errors occur if the link to the model is lost or if the URL is not defined for the entity. But I use a vie instance that is prepared before and which is working in other cases.

Any idea where to look? 


Thanks for your help!



Adrien

Henri Bergius

unread,
Dec 20, 2012, 4:15:50 AM12/20/12
to crea...@googlegroups.com
Hi,

On Wed, Dec 19, 2012 at 5:34 PM, Adrien Nicolet <adrien....@liip.ch> wrote:
> options.entity.vie.entities.add(myEntity);
> jQuery('body').midgardStorage('saveRemote', myEntity);
> But I now get the following backbone error after the last line: Error: A
> "url" property or function must be specified.

This is a timing issue. Create's Storage widget listens to the 'add'
events on vie.entities, and attaches the correct URL callback to them
so that it can save. But in this case you're making the saveRemote
call before that happens, and so you get the "missing URL" error from
Backbone.

This should be fixable by ensuring the order is correct:

options.entity.vie.entities.add(myEntity);
setTimeout(function () {
jQuery('body').midgardStorage('saveRemote', myEntity);
}, 0);

This way the event gets a chance to fire first.

> Adrien

/Henri

--
Henri Bergius
Motorcycle Adventures and Free Software
http://bergie.iki.fi/

Jabber: henri....@gmail.com
Microblogs: @bergie

Adrien Nicolet

unread,
Dec 21, 2012, 8:46:37 AM12/21/12
to crea...@googlegroups.com
The setTimeout solution didn't solve my problem. However, we figured out that the url can be set directly to the entity:

myEntity.url = function() {
    return 'the-url';
};

But I refactored the whole thing and I don't need it anymore, the url is correctly kept inside the VIE instance. So the A "url" property or function must be specified error doesn't appear anymore. 

So I was finally able to do what I wanted. It is functional, but improvements will be done soon. The work can be followed here: https://github.com/symfony-cmf/CreateBundle/pull/24. The file concerned is create-routes-handler.js. 


Special thanks to Bergie and David for the help!
Reply all
Reply to author
Forward
0 new messages