void test_wrap()
{
    testDiag("test_wrap");

    NTNameValuePtr nullPtr = NTNameValue::wrap(PVStructurePtr());
    testOk(nullPtr.get() == 0, "nullptr wrap");

    nullPtr = NTNameValue::wrap(
                getPVDataCreate()->createPVStructure(
                    NTField::get()->createTimeStamp()
                    )
                );
    testOk(nullPtr.get() == 0, "wrong type wrap");


    NTNameValueBuilderPtr builder = NTNameValue::createBuilder();
    testOk(builder.get() != 0, "Got builder");

    PVStructurePtr pvStructure = builder->
            value(pvString)->
            createPVStructure();
    testOk1(pvStructure.get() != 0);
    if (!pvStructure)
        return;

    testOk1(NTNameValue::isCompatible(pvStructure)==true);
    NTNameValuePtr ptr = NTNameValue::wrap(pvStructure);
    testOk(ptr.get() != 0, "wrap OK");

    ptr = NTNameValue::wrapUnsafe(pvStructure);
    testOk(ptr.get() != 0, "wrapUnsafe OK");
}
void test()
{
    RPCClientPtr channelRPC = 
        RPCClientPtr(RPCClient::create(channelName));
    bool result = channelRPC->connect(1.0);
    if(!result) {
        cout<< "connect failed\n";
        return;
    }
    NTNameValueBuilderPtr builder = NTNameValue::createBuilder();
    NTNameValuePtr ntnamevalue = builder ->
         value(pvString) ->
         add("function",fieldCreate->createScalar(pvString)) ->
         create();
    PVStructurePtr pv = ntnamevalue->getPVStructure();
    PVStringPtr pvFunction = pv->getSubField<PVString>("function");
    PVStringArrayPtr pvNames = pv->getSubField<PVStringArray>("name");
    PVStringArrayPtr pvValues = pv->getSubField<PVStringArray>("value");
    size_t n = 2;
    shared_vector<string> name(n);
    shared_vector<string> value(n);
    name[0] = string("configname");
    name[1] = string("servicename");
    value[0] = string("test");
    value[1] = string("masar");
    pvNames->replace(freeze(name));
    pvValues->replace(freeze(value));
    pvFunction->put("retrieveSnapshot");
    try {
cout << *ntnamevalue->getPVStructure() << endl;
        PVStructurePtr pvResponse = channelRPC->request(ntnamevalue->getPVStructure());
        cout << *pvResponse << endl;
    } catch (std::exception &e)
    {
        cout << e.what() << endl;
        return;
    }
    channelRPC->destroy();
}
void test_ntnameValue()
{
    testDiag("test_ntnameValue");

    NTNameValueBuilderPtr builder = NTNameValue::createBuilder();
    testOk(builder.get() != 0, "Got builder");

    NTNameValuePtr ntNameValue = builder->
            value(pvInt)->
            addDescriptor()->
            addAlarm()->
            addTimeStamp()->
            add("extra1",fieldCreate->createScalar(pvString)) ->
            add("extra2",fieldCreate->createScalarArray(pvString)) ->
            create();
    testOk1(ntNameValue.get() != 0);

    testOk1(NTNameValue::is_a(ntNameValue->getPVStructure()));
    testOk1(NTNameValue::isCompatible(ntNameValue->getPVStructure()));

    testOk1(ntNameValue->getPVStructure().get() != 0);
    testOk1(ntNameValue->getDescriptor().get() != 0);
    testOk1(ntNameValue->getAlarm().get() != 0);
    testOk1(ntNameValue->getTimeStamp().get() != 0);
    testOk1(ntNameValue->getName().get() != 0);
    testOk1(ntNameValue->getValue().get() != 0);

    //
    // example how to set name
    //
    PVStringArray::svector newName;
    newName.push_back("name1");
    newName.push_back("name2");
    newName.push_back("name3");

    PVStringArrayPtr pvNameField = ntNameValue->getName();
    pvNameField->replace(freeze(newName));

    //
    // example how to get name
    //
    PVStringArray::const_svector name(pvNameField->view());

    testOk1(name.size() == 3);
    testOk1(name[0] == "name1");
    testOk1(name[1] == "name2");
    testOk1(name[2] == "name3");

    //
    // example how to set value
    //
    PVIntArray::svector newValue;
    newValue.push_back(1);
    newValue.push_back(2);
    newValue.push_back(8);

    PVIntArrayPtr pvValueField = ntNameValue->getValue<PVIntArray>();
    pvValueField->replace(freeze(newValue));

    //
    // example how to get column value
    //
    PVIntArray::const_svector value(pvValueField->view());

    testOk1(value.size() == 3);
    testOk1(value[0] == 1);
    testOk1(value[1] == 2);
    testOk1(value[2] == 8);

    //
    // timeStamp ops
    //
    PVTimeStamp pvTimeStamp;
    if (ntNameValue->attachTimeStamp(pvTimeStamp))
    {
        testPass("timeStamp attach");

        // example how to set current time
        TimeStamp ts;
        ts.getCurrent();
        pvTimeStamp.set(ts);

        // example how to get EPICS time
        TimeStamp ts2;
        pvTimeStamp.get(ts2);
        testOk1(ts2.getEpicsSecondsPastEpoch() != 0);
    }
    else
        testFail("timeStamp attach fail");

    //
    // alarm ops
    //
    PVAlarm pvAlarm;
    if (ntNameValue->attachAlarm(pvAlarm))
    {
        testPass("alarm attach");

        // example how to set an alarm
        Alarm alarm;
        alarm.setStatus(deviceStatus);
        alarm.setSeverity(minorAlarm);
        alarm.setMessage("simulation alarm");
        pvAlarm.set(alarm);
    }
    else
        testFail("alarm attach fail");

    //
    // set descriptor
    //
    ntNameValue->getDescriptor()->put("This is a test NTNameValue");

    // dump NTNameValue
    std::cout << *ntNameValue->getPVStructure() << std::endl;

}