BSON-XS

 view release on metacpan or  search on metacpan

xs/XS.xs  view on Meta::CPAN


    bson_iter_dbpointer(iter, &len, &collection, &oid_ptr);

    if ( ! is_utf8_string((const U8*)collection,len)) {
      croak( "Invalid UTF-8 detected while decoding BSON" );
    }

    coll = newSVpvn(collection, len);
    SvUTF8_on(coll);

    oid = new_object_from_pairs(
      "BSON::OID", "oid", newSVpvn((const char *) oid_ptr->bytes, 12), NULL
    );

    value = new_object_from_pairs( "BSON::DBRef",
      "ref", sv_2mortal(coll), "id", sv_2mortal(oid), NULL
    );

    break;
  }
  default: {
    /* Should already have been caught during bson_validate() but in case not: */
    croak("unsupported BSON type \\x%02X for key '%s'.  Are you using the latest version of BSON::XS?", bson_iter_type(iter), key );
  }
  }
  return value;
}

static SV *
bson_oid_to_sv (const bson_iter_t * iter) {
  HV *stash, *id_hv;

  const bson_oid_t * oid = bson_iter_oid(iter);

  id_hv = newHV();
  (void)hv_stores(id_hv, "oid", newSVpvn((const char *) oid->bytes, 12));

  stash = gv_stashpv("BSON::OID", 0);
  return sv_bless(newRV_noinc((SV *)id_hv), stash);
}

MODULE = BSON::XS       PACKAGE = BSON::XS

PROTOTYPES: DISABLE

void
_decode_bson(msg, options)
        SV *msg
        SV *options

    PREINIT:
        char * data;
        bson_t bson;
        bson_iter_t iter;
        size_t error_offset;
        STRLEN length;
        HV *opts;
        uint32_t invalid_type;
        const char *invalid_key;

    PPCODE:
        data = SvPV(msg, length);
        opts = NULL;

        if ( options ) {
            if ( SvROK(options) && SvTYPE(SvRV(options)) == SVt_PVHV ) {
                opts = (HV *) SvRV(options);
            }
            else {
                croak("options must be a reference to a hash");
            }
        }

        if ( ! bson_init_static(&bson, (uint8_t *) data, length) ) {
          croak("Error reading BSON document");
        }

        if ( ! bson_validate(&bson, BSON_VALIDATE_NONE, &error_offset, &invalid_key, &invalid_type) ) {
          croak( "Invalid BSON input" );
        }

        if ( invalid_type != 0 ) {
            croak("unsupported BSON type \\x%02X for key '%s'.  Are you using the latest version of BSON::XS?", invalid_type, invalid_key );
        }

        if ( ! bson_iter_init(&iter, &bson) ) {
          croak( "Error creating BSON iterator" );
        }

        XPUSHs(sv_2mortal(bson_doc_to_hashref(&iter, opts, 0, TRUE)));

void
_encode_bson(doc, options)
        SV *doc
        SV *options
    PREINIT:
        bson_t * bson;
        HV *opts;
    PPCODE:
        opts = NULL;
        bson = bson_new();
        if ( options ) {
            if ( SvROK(options) && SvTYPE(SvRV(options)) == SVt_PVHV ) {
                opts = (HV *) SvRV(options);
            }
            else {
                croak("options must be a reference to a hash");
            }
        }
        perl_mongo_sv_to_bson(bson, doc, opts);
        XPUSHs(sv_2mortal(newSVpvn((const char *)bson_get_data(bson), bson->len)));
        bson_destroy(bson);

SV *
_generate_oid ()
    PREINIT:
        bson_oid_t boid;
    CODE:
        bson_oid_init(&boid, NULL);
        RETVAL = newSVpvn((const char *) boid.bytes, 12);
    OUTPUT:
        RETVAL



( run in 0.754 second using v1.01-cache-2.11-cpan-71847e10f99 )