/
home
/
sjslayjy
/
public_html
/
theweavenest
/
vendor
/
ramsey
/
uuid
/
docs
/
nonstandard
/
Upload File
HOME
.. _nonstandard.guid: =================================== Globally Unique Identifiers (GUIDs) =================================== .. tip:: Using these techniques to work with GUIDs is useful if you're working with identifiers that have been stored in GUID byte order. For example, this is the case if working with the ``UNIQUEIDENTIFIER`` data type in Microsoft SQL Server. This is a GUID, stored as a 16-byte binary string. If working directly with the bytes, you may use the GUID functionality in ramsey/uuid to properly handle this data type. According to the Windows Dev Center article on `GUID structure`_, "GUIDs are the Microsoft implementation of the distributed computing environment (DCE) universally unique identifier." For all intents and purposes, a GUID string representation is identical to that of an `RFC 4122`_ UUID. For historical reasons, *the byte order is not*. The `.NET Framework documentation`_ explains: Note that the order of bytes in the returned byte array is different from the string representation of a Guid value. The order of the beginning four-byte group and the next two two-byte groups is reversed, whereas the order of the last two-byte group and the closing six-byte group is the same. This is best explained by example. .. code-block:: php :caption: Decoding a GUID from byte representation :name: nonstandard.guid.decode-bytes-example use Ramsey\Uuid\FeatureSet; use Ramsey\Uuid\UuidFactory; // The bytes of a GUID previously stored in some datastore. $guidBytes = hex2bin('0eab93fc9ec9584b975e9c5e68c53624'); $useGuids = true; $featureSet = new FeatureSet($useGuids); $factory = new UuidFactory($featureSet); $guid = $factory->fromBytes($guidBytes); printf( "Class: %s\nGUID: %s\nVersion: %d\nBytes: %s\n", get_class($guid), $guid->toString(), $guid->getFields()->getVersion(), bin2hex($guid->getBytes()) ); This transforms the bytes of a GUID, as represented by ``$guidBytes``, into a :php:class:`Ramsey\\Uuid\\Guid\\Guid` instance and prints out some details about it. It looks something like this: .. code-block:: text Class: Ramsey\Uuid\Guid\Guid GUID: fc93ab0e-c99e-4b58-975e-9c5e68c53624 Version: 4 Bytes: 0eab93fc9ec9584b975e9c5e68c53624 Note the difference between the string GUID and the bytes. The bytes are arranged like this: .. code-block:: text 0e ab 93 fc 9e c9 58 4b 97 5e 9c 5e 68 c5 36 24 In an `RFC 4122`_ UUID, the bytes are stored in the same order as you see presented in the string representation. This is often called *network byte order*, or *big-endian* order. In a GUID, the order of the bytes are reversed in each grouping for the first 64 bits and stored in *little-endian* order. The remaining 64 bits are stored in network byte order. See `Endianness <#nonstandard-guid-endianness>`_ to learn more. .. caution:: The bytes themselves do not indicate their order. If you decode GUID bytes as a UUID or UUID bytes as a GUID, you will get the wrong values. However, you can always create a GUID or UUID from the same string value; the bytes for each will be in a different order, even though the string is the same. The key is to know ahead of time in what order the bytes are stored. Then, you will be able to decode them using the correct approach. Converting GUIDs to UUIDs ######################### Continuing from the example, :ref:`nonstandard.guid.decode-bytes-example`, we can take the GUID string representation and convert it into a standard UUID. .. code-block:: php :caption: Convert a GUID to a UUID :name: nonstandard.guid.convert-example $uuid = Uuid::fromString($guid->toString()); printf( "Class: %s\nUUID: %s\nVersion: %d\nBytes: %s\n", get_class($uuid), $uuid->toString(), $uuid->getFields()->getVersion(), bin2hex($uuid->getBytes()) ); Because the GUID was a version 4, random UUID, this creates an instance of :php:class:`Ramsey\\Uuid\\Rfc4122\\UuidV4` from the GUID string and prints out a few details about it. It looks something like this: .. code-block:: text Class: Ramsey\Uuid\Rfc4122\UuidV4 UUID: fc93ab0e-c99e-4b58-975e-9c5e68c53624 Version: 4 Bytes: fc93ab0ec99e4b58975e9c5e68c53624 Note how the UUID string is identical to the GUID string. However, the byte order is different, since they are in big-endian order. The bytes are now arranged like this: .. code-block:: text fc 93 ab 0e c9 9e 4b 58 97 5e 9c 5e 68 c5 36 24 .. admonition:: Endianness :name: nonstandard.guid.endianness Big-endian and little-endian refer to the ordering of bytes in a multi-byte number. Big-endian order places the most significant byte first, followed by the other bytes in descending order. Little-endian order places the least significant byte first, followed by the other bytes in ascending order. Take the hexadecimal number ``0x1234``, for example. In big-endian order, the bytes are stored as ``12 34``, and in little-endian order, they are stored as ``34 12``. In either case, the number is still ``0x1234``. Networking protocols usually use big-endian ordering, while computer processor architectures often use little-endian ordering. The terms originated in Jonathan Swift's *Gulliver's Travels*, where the Lilliputians argue over which end of a hard-boiled egg is the best end to crack. .. _GUID structure: https://docs.microsoft.com/en-us/windows/win32/api/guiddef/ns-guiddef-guid#remarks .. _RFC 4122: https://tools.ietf.org/html/rfc4122 .. _.NET Framework documentation: https://docs.microsoft.com/en-us/dotnet/api/system.guid.tobytearray#remarks