Пример #1
0
/**
 * 
 * 将xml的parameters参数写入到jceOutputStream中
 * 
 * @param inXml 
 * @param _os 
 */
void XmlProxyCallback::_writeParameters(taf::JceOutputStream<taf::BufferWriter> &os)
{
	_xmlReq.IntoElem();
	int iTag = 0;
	while (_xmlReq.FindElem())
	{
		iTag ++;

		//忽略out参数
		if (TC_Common::lower(_xmlReq.GetAttrib("in")) == "true")
		{
			_writeField(iTag, _xmlReq.GetTagName(), _xmlReq.GetData(), os);
		}
	}

	_xmlReq.OutOfElem();
}
Пример #2
0
void XmlProxyCallback::_writeField(const int &iTag, const MCD_STR &sTagName, const MCD_STR &sData, taf::JceOutputStream<taf::BufferWriter> & os)
{
	if (TC_Common::lower(sTagName) == "bool")
	{
		taf::Bool bValue = TC_Common::upper(sData) == "TRUE";
		os.write(bValue, iTag);
	}
	else if (TC_Common::lower(sTagName) == "byte")
	{
		taf::Char cValue;
		if (sData.size() > 1)
		{
			cValue = TC_Common::x2c(sData);
		}
		os.write(cValue,iTag);
	}
	else if (TC_Common::lower(sTagName) == "short")
	{
		os.write(TC_Common::strto<taf::Short>(sData), iTag);
	}
	else if (TC_Common::lower(sTagName) == "int")
	{
		os.write(TC_Common::strto<taf::Int32>(sData), iTag);
	}
	else if (TC_Common::lower(sTagName) == "long")
	{
		os.write(TC_Common::strto<taf::Int64>(sData), iTag);
	}
	else if (TC_Common::lower(sTagName) == "float")
	{
		os.write(TC_Common::strto<taf::Float>(sData), iTag);
	}
	else if (TC_Common::lower(sTagName) == "double")
	{
		os.write(TC_Common::strto<taf::Double>(sData), iTag);
	}
	else if (TC_Common::lower(sTagName) == "string")
	{
		os.write(sData, iTag);
	}
	else if (TC_Common::lower(sTagName) == "enum")
	{
		os.write(TC_Common::strto<taf::Int32>(sData), iTag);
	}
	else if (TC_Common::lower(sTagName) == "struct")
	{
		DataHead h(DataHead::eStructBegin, iTag);
		h.writeTo(os);

		_xmlReq.IntoElem();
		while (_xmlReq.FindElem())
		{
			int iSubTag = TC_Common::strto<int>(_xmlReq.GetAttrib("tag"));
			_writeField(iSubTag, _xmlReq.GetTagName(), _xmlReq.GetData(), os);
		}
		_xmlReq.OutOfElem();

		h.setType(DataHead::eStructEnd);
		h.setTag(0);
		h.writeTo(os);
	}
	else if (TC_Common::lower(sTagName) == "vector")
	{
		DataHead h(DataHead::eList, iTag);
		h.writeTo(os);

		_xmlReq.IntoElem();
		int n = 0;
		taf::JceOutputStream<taf::BufferWriter> vectorCt;        
		while (_xmlReq.FindElem())
		{
			++ n;
			int iSubTag = 0;
			_writeField(iSubTag, _xmlReq.GetTagName(), _xmlReq.GetData(), vectorCt);
		}
		_xmlReq.OutOfElem();

		os.write(n, 0);
		os.writeBuf(vectorCt.getBuffer(), vectorCt.getLength());
	}
	else if (TC_Common::lower(sTagName) == "vector_char")
	{
		DataHead h(DataHead::eSimpleList, iTag);
		h.writeTo(os);

		DataHead hh(DataHead::eChar, 0);
		hh.writeTo(os);

		string sBin = TC_Common::str2bin(_xmlReq.GetData());        
		os.write(sBin.length(), 0);                
		os.writeBuf(sBin.c_str(), sBin.length());
	}
	else if (TC_Common::lower(sTagName) == "map")
	{
		DataHead h(DataHead::eMap, iTag);
		h.writeTo(os);

		_xmlReq.IntoElem();//into map
		int n = 0 ;
		taf::JceOutputStream<taf::BufferWriter> mapCt;        
		while (_xmlReq.FindElem())//find entry
		{
			++ n;
			_xmlReq.IntoElem();//into entry
			for (int i = 0 ; i < 2; i++)
			{
				if (_xmlReq.FindElem())//find key or value
				{
					_writeField(i, _xmlReq.GetTagName(), _xmlReq.GetData(), mapCt);
				}
			}
			_xmlReq.OutOfElem();//out entry
		}
		_xmlReq.OutOfElem();//out map

		os.write(n,0);        
		os.writeBuf(mapCt.getBuffer(), mapCt.getLength());
	}
}
Пример #3
0
BSONObj ObjectWrapper::toBSON() {
    if (getScope(_context)->getProto<BSONInfo>().instanceOf(_object)) {
        BSONObj* originalBSON = nullptr;
        bool altered;

        std::tie(originalBSON, altered) = BSONInfo::originalBSON(_context, _object);

        if (originalBSON && !altered)
            return *originalBSON;
    }

    JS::RootedId id(_context);

    // INCREDIBLY SUBTLE BEHAVIOR:
    //
    // (jcarey): Be very careful about how the Rooting API is used in
    // relationship to WriteFieldRecursionFrames. Mozilla'a API more or less
    // demands that the rooting types are on the stack and only manipulated as
    // regular objects, which we aren't doing here. The reason they do this is
    // because the rooting types must be global created and destroyed in an
    // entirely linear order. This is impossible to screw up in regular use,
    // but our unwinding of the recursion frames makes it easy to do here.
    //
    // The roots above need to be before the first frame is emplaced (so
    // they'll be destroyed after it) and none of the roots in the below code
    // (or in ValueWriter::writeThis) can live longer than until the call to
    // emplace() inside ValueWriter. The runtime asserts enabled by MozJS's
    // debug mode will catch runtime errors, but be aware of how difficult this
    // is to get right and what to look for if one of them bites you.

    BSONObjBuilder b;

    {
        // NOTE: Keep the frames in a scope so that it is clear that
        // we always destroy them before we destroy 'b'. It is
        // important to do so: if 'b' is destroyed before the frames,
        // and we don't pop all of the frames (say, due to an
        // exeption), then the frame dtors would write to freed
        // memory.
        WriteFieldRecursionFrames frames;
        frames.emplace(_context, _object, nullptr, StringData{});

        // We special case the _id field in top-level objects and move it to the front.
        // This matches other drivers behavior and makes finding the _id field quicker in BSON.
        if (hasOwnField(InternedString::_id)) {
            _writeField(&b, InternedString::_id, &frames, frames.top().originalBSON);
        }

        while (frames.size()) {
            auto& frame = frames.top();

            // If the index is the same as length, we've seen all the keys at this
            // level and should go up a level
            if (frame.idx == frame.ids.length()) {
                frames.pop();
                continue;
            }

            if (frame.idx == 0 && frame.originalBSON && !frame.altered) {
                // If this is our first look at the object and it has an unaltered
                // bson behind it, move idx to the end so we'll roll up on the next
                // pass through the loop.
                frame.subbob_or(&b)->appendElements(*frame.originalBSON);
                frame.idx = frame.ids.length();
                continue;
            }

            id.set(frame.ids[frame.idx++]);

            if (frames.size() == 1) {
                IdWrapper idw(_context, id);

                // TODO: check if it's cheaper to just compare with an interned
                // string of "_id" rather than with ascii
                if (idw.isString() && idw.equalsAscii("_id")) {
                    continue;
                }
            }

            // writeField invokes ValueWriter with the frame stack, which will push
            // onto frames for subobjects, which will effectively recurse the loop.
            _writeField(frame.subbob_or(&b), JS::HandleId(id), &frames, frame.originalBSON);
        }
    }

    const int sizeWithEOO = b.len() + 1 /*EOO*/ - 4 /*BSONObj::Holder ref count*/;
    uassert(17260,
            str::stream() << "Converting from JavaScript to BSON failed: "
                          << "Object size "
                          << sizeWithEOO
                          << " exceeds limit of "
                          << BSONObjMaxInternalSize
                          << " bytes.",
            sizeWithEOO <= BSONObjMaxInternalSize);

    return b.obj();
}