VirtualBox

Changeset 74402 in vbox


Ignore:
Timestamp:
Sep 21, 2018 9:25:55 AM (6 years ago)
Author:
vboxsync
Message:

IPRT/rest: Implemented array and string-map support for deserializating polymorphic objects. bugref:9167

Location:
trunk
Files:
9 edited

Legend:

Unmodified
Added
Removed
  • trunk/include/iprt/cpp/restanyobject.h

    r74387 r74402  
    113113    /** Factory method. */
    114114    static DECLCALLBACK(RTCRestObjectBase *) createInstance(void);
     115    /** Deserialization w/ instantiation. */
     116    static FNDESERIALIZEINSTANCEFROMJSON deserializeInstanceFromJson;
    115117
    116118protected:
  • trunk/include/iprt/cpp/restarray.h

    r74387 r74402  
    147147
    148148    /**
     149     * For accessing the static deserializeInstanceFromJson() method of the value.
     150     */
     151    virtual int deserializeValueInstanceFromJson(RTCRestJsonCursor const &a_rCursor, RTCRestObjectBase **a_ppInstance) = 0;
     152
     153    /**
    149154     * Worker for the copy constructor and the assignment operator.
    150155     *
     
    244249    }
    245250
     251    /** @copydoc RTCRestObjectBase::FNDESERIALIZEINSTANCEFROMJSON */
     252    static DECLCALLBACK(int) deserializeInstanceFromJson(RTCRestJsonCursor const &a_rCursor, RTCRestObjectBase **a_ppInstance)
     253    {
     254        *a_ppInstance = new (std::nothrow) RTCRestArray<ElementType>();
     255        if (*a_ppInstance)
     256            return (*a_ppInstance)->deserializeFromJson(a_rCursor);
     257        return a_rCursor.m_pPrimary->addError(a_rCursor, VERR_NO_MEMORY, "Out of memory");
     258    }
     259
    246260
    247261    /**
     
    418432        return new (std::nothrow) ElementType();
    419433    }
     434
     435    virtual int deserializeValueInstanceFromJson(RTCRestJsonCursor const &a_rCursor, RTCRestObjectBase **a_ppInstance) RT_OVERRIDE
     436    {
     437        return ElementType::deserializeInstanceFromJson(a_rCursor, a_ppInstance);
     438    }
    420439};
    421440
  • trunk/include/iprt/cpp/restbase.h

    r74390 r74402  
    312312
    313313    /**
     314     * Polymorphic JSON deserialization helper that instantiate the matching class using
     315     * the discriminator field.
     316     *
     317     * @returns IPRT status code.
     318     * @param   a_rCursor    The JSON cursor.
     319     * @param   a_ppInstance Where to return the deserialized instance.
     320     *                       May return an object on failure.
     321     */
     322    typedef DECLCALLBACK(int) FNDESERIALIZEINSTANCEFROMJSON(RTCRestJsonCursor const &a_rCursor, RTCRestObjectBase **a_ppInstance);
     323    /** Pointer to a FNDESERIALIZEINSTANCEFROMJSON function. */
     324    typedef FNDESERIALIZEINSTANCEFROMJSON *PFNDESERIALIZEINSTANCEFROMJSON;
     325
     326    /**
    314327     * Flags for toString().
    315328     *
     
    444457    /** Factory method. */
    445458    static DECLCALLBACK(RTCRestObjectBase *) createInstance(void);
     459    /** Deserialization w/ instantiation. */
     460    static FNDESERIALIZEINSTANCEFROMJSON deserializeInstanceFromJson;
    446461
    447462public:
     
    487502    /** Factory method. */
    488503    static DECLCALLBACK(RTCRestObjectBase *) createInstance(void);
     504    /** Deserialization w/ instantiation. */
     505    static FNDESERIALIZEINSTANCEFROMJSON deserializeInstanceFromJson;
    489506
    490507public:
     
    530547    /** Factory method. */
    531548    static DECLCALLBACK(RTCRestObjectBase *) createInstance(void);
     549    /** Deserialization w/ instantiation. */
     550    static FNDESERIALIZEINSTANCEFROMJSON deserializeInstanceFromJson;
    532551
    533552public:
     
    573592    /** Factory method. */
    574593    static DECLCALLBACK(RTCRestObjectBase *) createInstance(void);
     594    /** Deserialization w/ instantiation. */
     595    static FNDESERIALIZEINSTANCEFROMJSON deserializeInstanceFromJson;
    575596
    576597public:
     
    616637    /** Factory method. */
    617638    static DECLCALLBACK(RTCRestObjectBase *) createInstance(void);
     639    /** Deserialization w/ instantiation. */
     640    static FNDESERIALIZEINSTANCEFROMJSON deserializeInstanceFromJson;
    618641
    619642public:
     
    663686    /** Factory method. */
    664687    static DECLCALLBACK(RTCRestObjectBase *) createInstance(void);
     688    /** Deserialization w/ instantiation. */
     689    static FNDESERIALIZEINSTANCEFROMJSON deserializeInstanceFromJson;
    665690
    666691    /** @name RTCString assignment methods we need to replace to manage the null indicator
     
    729754    /** Factory method. */
    730755    static DECLCALLBACK(RTCRestObjectBase *) createInstance(void);
     756    /** Deserialization w/ instantiation. */
     757    static FNDESERIALIZEINSTANCEFROMJSON deserializeInstanceFromJson;
    731758
    732759    /** Date formats. */
     
    9921019
    9931020    /** Factory method. */
    994     static DECLCALLBACK(RTCRestObjectBase *) createInstance(void) { return new (std::nothrow) RTCRestStringEnum(); }
     1021    static DECLCALLBACK(RTCRestObjectBase *) createInstance(void)
     1022    {
     1023        return new (std::nothrow) RTCRestStringEnum();
     1024    }
     1025
     1026    /** @copydoc RTCRestObjectBase::FNDESERIALIZEINSTANCEFROMJSON */
     1027    static DECLCALLBACK(int) deserializeInstanceFromJson(RTCRestJsonCursor const &a_rCursor, RTCRestObjectBase **a_ppInstance)
     1028    {
     1029        *a_ppInstance = new (std::nothrow) RTCRestStringEnum();
     1030        if (*a_ppInstance)
     1031            return (*a_ppInstance)->deserializeFromJson(a_rCursor);
     1032        return a_rCursor.m_pPrimary->addError(a_rCursor, VERR_NO_MEMORY, "Out of memory");
     1033    }
    9951034
    9961035protected:
     
    10561095    /** Factory method. */
    10571096    static DECLCALLBACK(RTCRestObjectBase *) createInstance(void);
     1097    /** Deserialization w/ instantiation. */
     1098    static FNDESERIALIZEINSTANCEFROMJSON deserializeInstanceFromJson;
    10581099
    10591100protected:
  • trunk/include/iprt/cpp/reststringmap.h

    r74387 r74402  
    231231
    232232    /**
     233     * For accessing the static deserializeInstanceFromJson() method of the value.
     234     */
     235    virtual int deserializeValueInstanceFromJson(RTCRestJsonCursor const &a_rCursor, RTCRestObjectBase **a_ppInstance) = 0;
     236
     237    /**
    233238     * Worker for the copy constructor and the assignment operator.
    234239     *
     
    342347    }
    343348
     349    /** @copydoc RTCRestObjectBase::FNDESERIALIZEINSTANCEFROMJSON */
     350    static DECLCALLBACK(int) deserializeInstanceFromJson(RTCRestJsonCursor const &a_rCursor, RTCRestObjectBase **a_ppInstance)
     351    {
     352        *a_ppInstance = new (std::nothrow) RTCRestStringMap<ValueType>();
     353        if (*a_ppInstance)
     354            return (*a_ppInstance)->deserializeFromJson(a_rCursor);
     355        return a_rCursor.m_pPrimary->addError(a_rCursor, VERR_NO_MEMORY, "Out of memory");
     356    }
     357
    344358    /**
    345359     * Inserts the given object into the map.
     
    454468        return new (std::nothrow) ValueType();
    455469    }
     470
     471    virtual int deserializeValueInstanceFromJson(RTCRestJsonCursor const &a_rCursor, RTCRestObjectBase **a_ppInstance) RT_OVERRIDE
     472    {
     473        return ValueType::deserializeInstanceFromJson(a_rCursor, a_ppInstance);
     474    }
    456475};
    457476
  • trunk/src/VBox/Runtime/common/rest/RTCRestAnyObject.cpp

    r74386 r74402  
    580580}
    581581
     582
     583/**
     584 * @copydoc RTCRestObjectBase::FNDESERIALIZEINSTANCEFROMJSON
     585 */
     586/*static*/ DECLCALLBACK(int)
     587RTCRestAnyObject::deserializeInstanceFromJson(RTCRestJsonCursor const &a_rCursor, RTCRestObjectBase **a_ppInstance)
     588{
     589    RTCRestObjectBase *pObj = createInstance();
     590    *a_ppInstance = pObj;
     591    if (pObj)
     592        return pObj->deserializeFromJson(a_rCursor);
     593    return a_rCursor.m_pPrimary->addError(a_rCursor, VERR_NO_MEMORY, "Out of memory");
     594}
     595
  • trunk/src/VBox/Runtime/common/rest/RTCRestArrayBase.cpp

    r74386 r74402  
    156156        for (size_t idxName = 0;; idxName++)
    157157        {
     158            /* Setup sub-cursor. */
    158159            RTCRestJsonCursor SubCursor(a_rCursor);
    159160            int rc = RTJsonIteratorQueryValue(hIterator, &SubCursor.m_hValue, &SubCursor.m_pszName);
    160161            if (RT_SUCCESS(rc))
    161162            {
    162                 RTCRestObjectBase *pObj = createValue();
     163                char szName[32];
     164                RTStrPrintf(szName, sizeof(szName), "[%u]", idxName);
     165                SubCursor.m_pszName = szName;
     166
     167                /* Call the static deserializeInstanceFromJson method of the value class.  */
     168                RTCRestObjectBase *pObj = NULL;
     169                rc = deserializeValueInstanceFromJson(SubCursor, &pObj);
     170                if (RT_SUCCESS(rc))
     171                    Assert(pObj);
     172                else if (RT_SUCCESS(rcRet))
     173                    rcRet = rc;
    163174                if (pObj)
    164175                {
    165                     char szName[32];
    166                     RTStrPrintf(szName, sizeof(szName), "[%u]", idxName);
    167                     SubCursor.m_pszName = szName;
    168 
    169                     rc = pObj->deserializeFromJson(SubCursor);
    170                     if (RT_SUCCESS(rc))
    171                     { /* likely */ }
    172                     else if (RT_SUCCESS(rcRet))
    173                         rcRet = rc;
    174 
    175176                    rc = insertWorker(~(size_t)0, pObj, false /*a_fReplace*/);
    176177                    if (RT_SUCCESS(rc))
     
    183184                    }
    184185                }
    185                 else
    186                     rcRet = a_rCursor.m_pPrimary->addError(a_rCursor, rc, "Failed to create new value object");
    187186            }
    188187            else
  • trunk/src/VBox/Runtime/common/rest/RTCRestStringMapBase.cpp

    r74386 r74402  
    144144        for (;;)
    145145        {
     146            /* Set up the sub-cursor. */
    146147            RTCRestJsonCursor SubCursor(a_rCursor);
    147148            int rc = RTJsonIteratorQueryValue(hIterator, &SubCursor.m_hValue, &SubCursor.m_pszName);
    148149            if (RT_SUCCESS(rc))
    149150            {
    150                 RTCRestObjectBase *pObj = createValue();
     151                /* Call the static deserializeInstanceFromJson method of the value class.  */
     152                RTCRestObjectBase *pObj = NULL;
     153                rc = deserializeValueInstanceFromJson(a_rCursor, &pObj);
     154                if (RT_SUCCESS(rc))
     155                    Assert(pObj);
     156                else if (RT_SUCCESS(rcRet))
     157                    rcRet = rc;
    151158                if (pObj)
    152159                {
    153                     rc = pObj->deserializeFromJson(SubCursor);
    154                     if (RT_SUCCESS(rc))
    155                     { /* likely */ }
    156                     else if (RT_SUCCESS(rcRet))
    157                         rcRet = rc;
    158 
     160                    /* Insert the value. */
    159161                    rc = putWorker(SubCursor.m_pszName, pObj, true /*a_fReplace*/);
    160162                    if (rc == VINF_SUCCESS)
     
    174176                    }
    175177                }
    176                 else
    177                     rcRet = a_rCursor.m_pPrimary->addError(a_rCursor, rc, "Failed to create new value object");
    178178            }
    179179            else
  • trunk/src/VBox/Runtime/common/rest/rest-binary.cpp

    r74386 r74402  
    251251{
    252252    return new (std::nothrow) RTCRestBinary();
     253}
     254
     255
     256/**
     257 * @copydoc RTCRestObjectBase::FNDESERIALIZEINSTANCEFROMJSON
     258 */
     259/*static*/ DECLCALLBACK(int)
     260RTCRestBinary::deserializeInstanceFromJson(RTCRestJsonCursor const &a_rCursor, RTCRestObjectBase **a_ppInstance)
     261{
     262    RTCRestObjectBase *pObj;
     263    *a_ppInstance = pObj = createInstance();
     264    if (pObj)
     265        return pObj->deserializeFromJson(a_rCursor);
     266    return a_rCursor.m_pPrimary->addError(a_rCursor, VERR_NO_MEMORY, "Out of memory");
    253267}
    254268
  • trunk/src/VBox/Runtime/common/rest/rest-primary-object-types.cpp

    r74386 r74402  
    131131
    132132
     133/**
     134 * @copydoc RTCRestObjectBase::FNDESERIALIZEINSTANCEFROMJSON
     135 */
     136/*static*/ DECLCALLBACK(int)
     137RTCRestBool::deserializeInstanceFromJson(RTCRestJsonCursor const &a_rCursor, RTCRestObjectBase **a_ppInstance)
     138{
     139    RTCRestObjectBase *pObj = createInstance();
     140    *a_ppInstance = pObj;
     141    if (pObj)
     142        return pObj->deserializeFromJson(a_rCursor);
     143    return a_rCursor.m_pPrimary->addError(a_rCursor, VERR_NO_MEMORY, "Out of memory");
     144}
     145
     146
    133147/** Default constructor. */
    134148RTCRestBool::RTCRestBool()
     
    307321
    308322
     323/**
     324 * @copydoc RTCRestObjectBase::FNDESERIALIZEINSTANCEFROMJSON
     325 */
     326/*static*/ DECLCALLBACK(int)
     327RTCRestInt64::deserializeInstanceFromJson(RTCRestJsonCursor const &a_rCursor, RTCRestObjectBase **a_ppInstance)
     328{
     329    RTCRestObjectBase *pObj = createInstance();
     330    *a_ppInstance = pObj;
     331    if (pObj)
     332        return pObj->deserializeFromJson(a_rCursor);
     333    return a_rCursor.m_pPrimary->addError(a_rCursor, VERR_NO_MEMORY, "Out of memory");
     334}
     335
     336
    309337/** Default constructor. */
    310338RTCRestInt64::RTCRestInt64()
     
    474502{
    475503    return new (std::nothrow) RTCRestInt32();
     504}
     505
     506
     507/**
     508 * @copydoc RTCRestObjectBase::FNDESERIALIZEINSTANCEFROMJSON
     509 */
     510/*static*/ DECLCALLBACK(int)
     511RTCRestInt32::deserializeInstanceFromJson(RTCRestJsonCursor const &a_rCursor, RTCRestObjectBase **a_ppInstance)
     512{
     513    RTCRestObjectBase *pObj = createInstance();
     514    *a_ppInstance = pObj;
     515    if (pObj)
     516        return pObj->deserializeFromJson(a_rCursor);
     517    return a_rCursor.m_pPrimary->addError(a_rCursor, VERR_NO_MEMORY, "Out of memory");
    476518}
    477519
     
    653695
    654696
     697/**
     698 * @copydoc RTCRestObjectBase::FNDESERIALIZEINSTANCEFROMJSON
     699 */
     700/*static*/ DECLCALLBACK(int)
     701RTCRestInt16::deserializeInstanceFromJson(RTCRestJsonCursor const &a_rCursor, RTCRestObjectBase **a_ppInstance)
     702{
     703    RTCRestObjectBase *pObj = createInstance();
     704    *a_ppInstance = pObj;
     705    if (pObj)
     706        return pObj->deserializeFromJson(a_rCursor);
     707    return a_rCursor.m_pPrimary->addError(a_rCursor, VERR_NO_MEMORY, "Out of memory");
     708}
     709
     710
    655711/** Default constructor. */
    656712RTCRestInt16::RTCRestInt16()
     
    827883    return new (std::nothrow) RTCRestDouble();
    828884}
     885
     886
     887/**
     888 * @copydoc RTCRestObjectBase::FNDESERIALIZEINSTANCEFROMJSON
     889 */
     890/*static*/ DECLCALLBACK(int)
     891RTCRestDouble::deserializeInstanceFromJson(RTCRestJsonCursor const &a_rCursor, RTCRestObjectBase **a_ppInstance)
     892{
     893    RTCRestObjectBase *pObj = createInstance();
     894    *a_ppInstance = pObj;
     895    if (pObj)
     896        return pObj->deserializeFromJson(a_rCursor);
     897    return a_rCursor.m_pPrimary->addError(a_rCursor, VERR_NO_MEMORY, "Out of memory");
     898}
     899
    829900
    830901/** Default constructor. */
     
    10581129
    10591130
     1131/**
     1132 * @copydoc RTCRestObjectBase::FNDESERIALIZEINSTANCEFROMJSON
     1133 */
     1134/*static*/ DECLCALLBACK(int)
     1135RTCRestString::deserializeInstanceFromJson(RTCRestJsonCursor const &a_rCursor, RTCRestObjectBase **a_ppInstance)
     1136{
     1137    RTCRestObjectBase *pObj = createInstance();
     1138    *a_ppInstance = pObj;
     1139    if (pObj)
     1140        return pObj->deserializeFromJson(a_rCursor);
     1141    return a_rCursor.m_pPrimary->addError(a_rCursor, VERR_NO_MEMORY, "Out of memory");
     1142}
     1143
     1144
    10601145/** Default constructor. */
    10611146RTCRestString::RTCRestString()
     
    13581443*   RTCRestDate implementation                                                                                                   *
    13591444*********************************************************************************************************************************/
     1445/*static*/ DECLCALLBACK(RTCRestObjectBase *) RTCRestDate::createInstance(void)
     1446{
     1447    return new (std::nothrow) RTCRestDate();
     1448}
     1449
     1450
     1451/**
     1452 * @copydoc RTCRestObjectBase::FNDESERIALIZEINSTANCEFROMJSON
     1453 */
     1454/*static*/ DECLCALLBACK(int)
     1455RTCRestDate::deserializeInstanceFromJson(RTCRestJsonCursor const &a_rCursor, RTCRestObjectBase **a_ppInstance)
     1456{
     1457    RTCRestObjectBase *pObj = createInstance();
     1458    *a_ppInstance = pObj;
     1459    if (pObj)
     1460        return pObj->deserializeFromJson(a_rCursor);
     1461    return a_rCursor.m_pPrimary->addError(a_rCursor, VERR_NO_MEMORY, "Out of memory");
     1462}
     1463
    13601464
    13611465RTCRestDate::RTCRestDate()
     
    15321636}
    15331637
    1534 
    1535 /*static*/ DECLCALLBACK(RTCRestObjectBase *) RTCRestDate::createInstance(void)
    1536 {
    1537     return new (std::nothrow) RTCRestDate();
    1538 }
    15391638
    15401639int RTCRestDate::assignValue(PCRTTIMESPEC a_pTimeSpec, kFormat a_enmFormat)
Note: See TracChangeset for help on using the changeset viewer.

© 2024 Oracle Support Privacy / Do Not Sell My Info Terms of Use Trademark Policy Automated Access Etiquette