Skip to content

Commit eb87998

Browse files
committed
ObjectId constructor translates a hex string (24 characters) into a 12 byte object id
1 parent 9f7076d commit eb87998

3 files changed

Lines changed: 46 additions & 28 deletions

File tree

MongoDB/include/Poco/MongoDB/ObjectId.h

Lines changed: 31 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -46,8 +46,12 @@ class MongoDB_API ObjectId
4646
public:
4747
typedef SharedPtr<ObjectId> Ptr;
4848

49-
ObjectId(const std::string& id = "");
50-
/// Constructor
49+
ObjectId(const std::string& id);
50+
/// Constructor. The string must contain a hexidecimal representation
51+
/// of an object id. This means a string of 24 characters.
52+
53+
ObjectId(const ObjectId& copy);
54+
/// Copy constructor.
5155

5256
virtual ~ObjectId();
5357
/// Destructor
@@ -61,10 +65,19 @@ class MongoDB_API ObjectId
6165
/// of the ID char array.
6266

6367
private:
68+
69+
ObjectId();
70+
/// Constructor. Creates an empty Id
71+
6472
unsigned char _id[12];
6573

6674
friend class BSONWriter;
6775
friend class BSONReader;
76+
friend class Document;
77+
78+
static int fromHex(char c);
79+
80+
static char fromHex(const char* c);
6881
};
6982

7083

@@ -79,6 +92,21 @@ inline Timestamp ObjectId::timestamp() const
7992
return Timestamp::fromEpochTime((time_t) time);
8093
}
8194

95+
inline int ObjectId::fromHex(char c)
96+
{
97+
if ( '0' <= c && c <= '9' )
98+
return c - '0';
99+
if ( 'a' <= c && c <= 'f' )
100+
return c - 'a' + 10;
101+
if ( 'A' <= c && c <= 'F' )
102+
return c - 'A' + 10;
103+
return 0xff;
104+
}
105+
106+
inline char ObjectId::fromHex(const char* c)
107+
{
108+
return (char)((fromHex(c[0]) << 4 ) | fromHex(c[1]));
109+
}
82110

83111
// BSON Embedded Document
84112
// spec: ObjectId
@@ -89,7 +117,7 @@ struct ElementTraits<ObjectId::Ptr>
89117

90118
static std::string toString(const ObjectId::Ptr& id,
91119
int indent = 0,
92-
const std::string& fmt = "%x")
120+
const std::string& fmt = "%02x")
93121
{
94122
return id->toString(fmt);
95123
}

MongoDB/src/ObjectId.cpp

Lines changed: 14 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -15,29 +15,33 @@
1515
// SPDX-License-Identifier: BSL-1.0
1616
//
1717

18-
1918
#include "Poco/MongoDB/ObjectId.h"
2019
#include "Poco/Format.h"
2120

2221

2322
namespace Poco {
2423
namespace MongoDB {
2524

25+
ObjectId::ObjectId()
26+
{
27+
memset(_id, 0, sizeof(_id));
28+
}
2629

2730
ObjectId::ObjectId(const std::string& id)
2831
{
29-
if (id.size() == 12)
30-
{
31-
std::string::const_iterator it = id.begin();
32-
std::string::const_iterator end = id.end();
33-
for (int i = 0; i < 12; ++it, ++i) _id[i] = *it;
34-
}
35-
else if (id.size())
36-
{
37-
throw Poco::InvalidArgumentException("ID must be 12 characters long.");
32+
poco_assert_dbg(id.size() == 24);
33+
34+
const char *p = id.c_str();
35+
for (std::size_t i = 0; i < 12; ++i) {
36+
_id[i] = fromHex(p);
37+
p += 2;
3838
}
3939
}
4040

41+
ObjectId::ObjectId(const ObjectId& copy)
42+
{
43+
memcpy(_id, copy._id, sizeof(_id));
44+
}
4145

4246
ObjectId::~ObjectId()
4347
{

MongoDB/testsuite/src/MongoDBTest.cpp

Lines changed: 1 addition & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -402,21 +402,7 @@ void MongoDBTest::testConnectionPool()
402402

403403
void MongoDBTest::testObjectID()
404404
{
405-
std::string str;
406-
str.append(1, (char) 0x53);
407-
str.append(1, (char) 0x6A);
408-
str.append(1, (char) 0xEE);
409-
str.append(1, (char) 0xBB);
410-
str.append(1, (char) 0xA0);
411-
str.append(1, (char) 0x81);
412-
str.append(1, (char) 0xDE);
413-
str.append(1, (char) 0x68);
414-
str.append(1, (char) 0x15);
415-
str.append(1, (char) 0x00);
416-
str.append(1, (char) 0x00);
417-
str.append(1, (char) 0x02);
418-
419-
ObjectId oid(str);
405+
ObjectId oid("536aeebba081de6815000002");
420406
std::string str2 = oid.toString();
421407
assert(str2 == "536aeebba081de6815000002");
422408
}

0 commit comments

Comments
 (0)