Как создать коллекцию сложного типа в olingo

Я стараюсь следовать нижеприведенному документу olingo, чтобы создать сервис odata.

AnnotationProcessor

Но мне не удается создать сущность со свойством, тип которого является List of ComplexType. У любого есть пример этого. Или это просто не поддерживается?

2 ответа

Может быть , ответ Утсава был верным в тот момент, но Odata v4 действительно поддерживает сущность со свойством, тип которого " List of ComplexType".
Доказательство : в этом примере entityType Person имеет свойство AddressInfo, а его тип является коллекцией ComplexType:

<ComplexType Name="Location" OpenType="true">
  <Property Name="Address" Type="Edm.String" Nullable="false"/>
  <Property Name="City" Type="Microsoft.OData.SampleService.Models.TripPin.City" Nullable="false"/>
</ComplexType>
...
<EntityType Name="Person" OpenType="true">
  <Property Name="AddressInfo" Type="Collection(Microsoft.OData.SampleService.Models.TripPin.Location)"/>
...
</EntityType>

Что касается реализации Olingo, в вашем провайдере CSDL вы должны правильно определить сущность вашего сложного типа, а затем определить свойство, которым вы хотите быть коллекцией этого сложного типа. Тогда вы должны правильно обработать результат.

1. Определение метаданных в CSDL-провайдере

В вашем провайдере getSchemas() Метод, который вы должны объявить ваши сложные типы:

    List <CsdlComplexType> complexTypes = new ArrayList<>();
    //...initialization of complexTypes list...
    schema.setComplexTypes(complexTypes);

В getEntityType() Метод, которым вы должны создать свое свойство как коллекцию объектов сложного типа:

    //...initialization of entityType...
    List<CsdlProperty> properties = new ArrayList<>();
    FullQualifiedName type;
    //...initialization of the type as a complex type...
    properties.add(new  CsdlProperty().setName("propertyName").setType(type).setCollection(true));
    entityType.setProperties(properties);
    //...

2. Обработка результата

В реализации вашего процессора вы должны правильно построить свою сущность: например, в readEntityCollection() метод EntityCollectionProcessor В реализации у вас должно быть что-то похожее на это:

    EntityCollection entities = new EntityCollection();
    List<Entity> eList = entities.getEntities();
    Entity e = new Entity();
    List<Map> data;
    //...initialization of complex type's data...
    List<ComplexValue> properties = new ArrayList<>();
    for (Object complexObject : data) {
        ComplexValue complexValue = new ComplexValue();
        for (Map.Entry<String, Object> entry : complexObject.entrySet()) {
                complexValue.getValue().add(new Property(null, entry.getKey(), ValueType.PRIMITIVE, entry.getValue()));
            }
        properties.add(complexValue);
    }
    e.addProperty(new Property(null, "propertyName", ValueType.COLLECTION_COMPLEX, properties););
    eList.add(e);

//...serialize and set the result to response

Я столкнулся с аналогичным требованием в моем проекте вчера. Тогда я заметил твой вопрос, который остался без ответа. Я реализовал подход, который работает для меня. Я описываю это ниже. Надеюсь, это поможет.

В двух словах: как я понимаю, так это то, что мы не можем использовать ComplexType для создания объекта в виде списка. Нам нужно использовать свойство навигации.

Постановка задачи: я должен прочитать сущность - EntityA. EntityA относится к EntityB. Отношение ОДИН-НА-МНОГО, т.е. EntityA содержит список EntityB. Типичное представление JSON будет следующим:

EntityA:{
"id":"entityA_1",
"entityBList":[
     {//EntityB Element
        "id" : "entityB_1",
        "description":"value1"
     },
     {//EntityB Element
        "id" : "entityB_2",
        "description":"value1"
     }
  ]
}

чтобы прочитать его со стороны клиента, я использую запрос OData с расширением - odata.sv/EntityA(1)?$expand=EntityB

Решение: чтобы включить описанный выше сценарий на стороне сервера, мне пришлось использовать свойства навигации.

  • Сначала мы создаем две отдельные сущности - EntityA и EntityB. Затем мы определяем отношения

    1. реализации метода getAssociation и
    2. в EdmProvider настройка свойств навигации при определении EntityA
  • Далее, во время чтения Entity(readEntity), мы предоставляем обратный вызов
    метод путем переопределения 'retrieveFeedResult' для заполнения EntityB.

У меня есть работающий POC для этого. Я могу также поделиться этим, если это необходимо. Сейчас у меня мало времени, поэтому просто поделились общим подходом. Надеюсь это поможет.

Другие вопросы по тегам