Beispiel #1
0
void ObjectWrapper::Key::del(JSContext* cx, JS::HandleObject o) {
    switch (_type) {
        case Type::Field:
            if (JS_DeleteProperty(cx, o, _field))
                return;
            break;
        case Type::Index:
            if (JS_DeleteElement(cx, o, _idx))
                return;
            break;
        case Type::Id: {
            JS::RootedId id(cx, _id);

            // For some reason JS_DeletePropertyById doesn't link
            if (JS_DeleteProperty(cx, o, IdWrapper(cx, id).toString().c_str()))
                return;
            break;
        }
        case Type::InternedString: {
            InternedStringId id(cx, _internedString);

            if (JS_DeleteProperty(cx, o, IdWrapper(cx, id).toString().c_str()))
                break;
        }
    }

    throwCurrentJSException(cx, ErrorCodes::InternalError, "Failed to delete value on a JSObject");
}
Beispiel #2
0
void BSONInfo::delProperty(JSContext* cx, JS::HandleObject obj, JS::HandleId id, bool* succeeded) {
    auto holder = getHolder(obj);

    if (holder) {
        if (holder->_readOnly) {
            uasserted(ErrorCodes::BadValue, "Read only object");
        }

        holder->_altered = true;

        holder->_removed.insert(IdWrapper(cx, id).toString());
    }

    *succeeded = true;
}
Beispiel #3
0
void BSONInfo::setProperty(
    JSContext* cx, JS::HandleObject obj, JS::HandleId id, bool strict, JS::MutableHandleValue vp) {
    auto holder = getHolder(obj);

    if (holder) {
        if (holder->_readOnly) {
            uasserted(ErrorCodes::BadValue, "Read only object");
        }

        auto iter = holder->_removed.find(IdWrapper(cx, id).toString());

        if (iter != holder->_removed.end()) {
            holder->_removed.erase(iter);
        }

        holder->_altered = true;
    }

    ObjectWrapper(cx, obj).defineProperty(id, vp, JSPROP_ENUMERATE);
}
Beispiel #4
0
void BSONInfo::resolve(JSContext* cx, JS::HandleObject obj, JS::HandleId id, bool* resolvedp) {
    auto holder = getHolder(obj);

    *resolvedp = false;

    if (!holder) {
        return;
    }

    IdWrapper idw(cx, id);

    if (!holder->_readOnly && holder->_removed.count(idw.toString())) {
        return;
    }

    ObjectWrapper o(cx, obj);

    std::string sname = IdWrapper(cx, id).toString();

    if (holder->_obj.hasField(sname)) {
        auto elem = holder->_obj[sname];

        JS::RootedValue vp(cx);

        ValueReader(cx, &vp).fromBSONElement(elem, holder->_readOnly);

        o.defineProperty(id, vp, JSPROP_ENUMERATE);

        if (!holder->_readOnly && (elem.type() == mongo::Object || elem.type() == mongo::Array)) {
            // if accessing a subobject, we have no way to know if
            // modifications are being made on writable objects

            holder->_altered = true;
        }

        *resolvedp = true;
    }
}