RequestFactoryEditorDriver doesn't save full graph even though “with()” is called. Is circular reference an issue?

笑着哭i 提交于 2019-12-13 00:52:53

问题


Could you guys please help me find where I made a mistake ?

I switched from SimpleBeanEditorDriver to RequestFactoryEditorDriver and my code no longer saves full graph even though with() method is called. But it correctly loads full graph in the constructor.

Could it be caused by circular reference between OrganizationProxy and PersonProxy ? I don't know what else to think :( It worked with SimpleBeanEditorDriver though.

Below is my client code. Let me know if you want me to add sources of proxies to this question (or you can see them here).

public class NewOrderView extends Composite
{
    interface Binder extends UiBinder<Widget, NewOrderView> {}
    private static Binder uiBinder = GWT.create(Binder.class);

    interface Driver extends RequestFactoryEditorDriver<OrganizationProxy, OrganizationEditor> {}
    Driver driver = GWT.create(Driver.class);

    @UiField
    Button save;

    @UiField
    OrganizationEditor orgEditor;

    AdminRequestFactory requestFactory;
    AdminRequestFactory.OrderRequestContext requestContext;

    OrganizationProxy organization;

    public NewOrderView()
    {
        initWidget(uiBinder.createAndBindUi(this));

        requestFactory = createFactory();
        requestContext = requestFactory.contextOrder();
        driver.initialize(requestFactory, orgEditor);

        String[] paths = driver.getPaths();
        createFactory().contextOrder().findOrganizationById(1).with(paths).fire(new Receiver<OrganizationProxy>()
        {
            @Override
            public void onSuccess(OrganizationProxy response)
            {
                if (response == null)
                {
                    organization = requestContext.create(OrganizationProxy.class);
                    organization.setContactPerson(requestContext.create(PersonProxy.class));
                } else
                    organization = requestContext.edit(response);

                driver.edit(organization, requestContext);
            }

            @Override
            public void onFailure(ServerFailure error)
            {
                createConfirmationDialogBox(error.getMessage()).center();
            }
        });
    }

    private static AdminRequestFactory createFactory()
    {
        AdminRequestFactory factory = GWT.create(AdminRequestFactory.class);
        factory.initialize(new SimpleEventBus());
        return factory;
    }

    @UiHandler("save")
    void buttonClick(ClickEvent e)
    {
        e.stopPropagation();
        save.setEnabled(false);

        try
        {
            AdminRequestFactory.OrderRequestContext ctx = (AdminRequestFactory.OrderRequestContext) driver.flush();
            if (!driver.hasErrors())
            {
                // Link to each other
                PersonProxy contactPerson = organization.getContactPerson();
                contactPerson.setOrganization(organization);

                String[] paths = driver.getPaths();
                ctx.saveOrganization(organization).with(paths).fire(new Receiver<Void>()
                {
                    @Override
                    public void onSuccess(Void arg0)
                    {
                        createConfirmationDialogBox("Saved!").center();
                    }

                    @Override
                    public void onFailure(ServerFailure error)
                    {
                        createConfirmationDialogBox(error.getMessage()).center();
                    }
                });
            }
        } finally
        {
            save.setEnabled(true);
        }
    }
}

回答1:


with() is only used for retrieval of information, so your with() use with a void return type is useless (but harmless).

Whether a full graph is persisted is entirely up to your server-side code, which is intimately bound to your persistence API (JPA, JDO, etc.)

First, check that the Organization object you receive in your save() method on the server-side is correctly populated. If it's not the case, check your Locators (and/or static findXxx methods) ; otherwise, check your save() method's code.

Judging from the code above, I can't see a reason why it wouldn't work.




回答2:


It took me some time to realize that the problem was the composite id of Person entity.

Below is the code snippet of PojoLocator that is used by my proxy entities.

public class PojoLocator extends Locator<DatastoreObject, Long>
{
    @Override
    public DatastoreObject find(Class<? extends DatastoreObject> clazz, Long id)
    {
    }

    @Override
    public Long getId(DatastoreObject domainObject)
    {
    }
}

In order to fetch child entity from DataStore you need to have id of a parent class. In order to achieve that I switched "ID class" for Locator<> to String which represents textual form of Objectify's Key<> class.

Here is how to looks now:

public class PojoLocator extends Locator<DatastoreObject, String>
{
    @Override
    public DatastoreObject find(Class<? extends DatastoreObject> clazz, String id)
    {
        Key<DatastoreObject> key = Key.create(id);
        return ofy.load(key);
    }

    @Override
    public String getId(DatastoreObject domainObject)
    {
        if (domainObject.getId() != null)
        {
            Key<DatastoreObject> key = ofy.fact().getKey(domainObject);
            return key.getString();
        } else
            return null;
    }
}

Please note that your implementation may slightly differ because I'm using Objectify4.



来源:https://stackoverflow.com/questions/9460639/requestfactoryeditordriver-doesnt-save-full-graph-even-though-with-is-calle

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!