{"id":176,"date":"2020-05-25T13:24:36","date_gmt":"2020-05-25T12:24:36","guid":{"rendered":"https:\/\/blog.thomarite.uk\/?p=176"},"modified":"2020-07-03T10:30:19","modified_gmt":"2020-07-03T09:30:19","slug":"mpls-segment-routing-arista-lab","status":"publish","type":"post","link":"https:\/\/blog.thomarite.uk\/index.php\/2020\/05\/25\/mpls-segment-routing-arista-lab\/","title":{"rendered":"MPLS Segment Routing &#8211; Arista Lab"},"content":{"rendered":"\n<p>We have been able to create some nice MPLS labs using GNS3 and Cisco IOS. In my current employer, we use Arista so I wanted to create a lab environment with Arista kit to simulate a MPLS Segment Routing network. Keeping in mind that I try to run everything on my laptop, using GNS3 + Arista is not an option. You need to use the Arista vEOS image in GNS3 and it demands 2GB RAM per device and 1 CPU. In the past, I think  I just managed to start two vEOS VMs before my laptop gave up. But Arista offers a version of EOS for containers.<\/p>\n\n\n\n<p>So, what&#8217;s the difference between a virtual machine (VM) and a container? Well, searching the internet is going to give you many all answers. In my very simplify way:<\/p>\n\n\n\n<ul class=\"wp-block-list\"><li>VM: needs an hypervisor to simulate hardware. It uses kernel and user space. It has a full OS. So it is like simulation a whole server\/pc (imagine a standalone house)<\/li><li>Container: runs in user space. Set of processes that are isolated from the rest of the system. Containers provide a way to virtualize an OS so that multiple workloads can run on a single OS instance (imagine an apartment in a building)<\/li><\/ul>\n\n\n\n<p>You just need to register in Arista web page to download a cEOS image.<\/p>\n\n\n\n<p>Regarding MPLS Segment Routing (or SPRING for Juniper) it is an evolution of the standard MPLS, that was originally developed to improve the routing performance in core networks: avoid to make a routing look-ups per packet in core devices was very expensive in 80\/90s (my very simplify way). MPLS started to being deployed around end 90s and became a defacto technology in all service providers.  More info <a href=\"https:\/\/en.wikipedia.org\/wiki\/Multiprotocol_Label_Switching\">here<\/a>.<\/p>\n\n\n\n<p>Segment Routing is still based in labels, but adds improvements as it doesnt need a protocol for label exchange (one less thing to worry about). As well, it is based in &#8220;source routing&#8221; as the sources chooses the path and encodes it in the packet.<\/p>\n\n\n\n<p>There are many sources in the internet that can explain MPLS SR better than me like all these:<\/p>\n\n\n\n<figure class=\"wp-block-embed-wordpress wp-block-embed is-type-wp-embed is-provider-packet-pushers\"><div class=\"wp-block-embed__wrapper\">\n<blockquote class=\"wp-embedded-content\" data-secret=\"pv2GIFrNh3\"><a href=\"https:\/\/packetpushers.net\/introduction-to-segment-routing\/\">Introduction to Segment Routing<\/a><\/blockquote><iframe loading=\"lazy\" class=\"wp-embedded-content\" sandbox=\"allow-scripts\" security=\"restricted\" style=\"position: absolute; clip: rect(1px, 1px, 1px, 1px);\" title=\"&#8220;Introduction to Segment Routing&#8221; &#8212; Packet Pushers\" src=\"https:\/\/packetpushers.net\/introduction-to-segment-routing\/embed\/#?secret=pv2GIFrNh3\" data-secret=\"pv2GIFrNh3\" width=\"600\" height=\"338\" frameborder=\"0\" marginwidth=\"0\" marginheight=\"0\" scrolling=\"no\"><\/iframe>\n<\/div><figcaption><a href=\"https:\/\/www.cisco.com\/c\/en\/us\/td\/docs\/ios-xml\/ios\/seg_routing\/configuration\/xe-3s\/segrt-xe-3s-book\/intro-seg-routing.html\">https:\/\/www.cisco.com\/c\/en\/us\/td\/docs\/ios-xml\/ios\/seg_routing\/configuration\/xe-3s\/segrt-xe-3s-book\/intro-seg-routing.html<\/a><br><br><a href=\"https:\/\/www.segment-routing.net\/tutorials\/\">https:\/\/www.segment-routing.net\/tutorials\/<\/a><br><\/figcaption><\/figure>\n\n\n\n<p>As we are going to use Arista, I based my learning in these presentations:<\/p>\n\n\n\n<p><a href=\"https:\/\/ripe77.ripe.net\/presentations\/16-20181015-SegmentRouting.pdf\">https:\/\/ripe77.ripe.net\/presentations\/16-20181015-SegmentRouting.pdf<\/a><\/p>\n\n\n\n<p><a href=\"https:\/\/www.netnod.se\/sites\/default\/files\/2018-03\/Peter%20Lundqvist_Arista_8.pdf\">https:\/\/www.netnod.se\/sites\/default\/files\/2018-03\/Peter%20Lundqvist_Arista_8.pdf<\/a><\/p>\n\n\n\n<p>And reading more Arista docs.<\/p>\n\n\n\n<p>All the code and how to build the lab is here: <\/p>\n\n\n\n<p><a href=\"https:\/\/github.com\/thomarite\/ceos-testing\">https:\/\/github.com\/thomarite\/ceos-testing<\/a><\/p>\n\n\n\n<figure class=\"wp-block-image size-large\"><img loading=\"lazy\" decoding=\"async\" width=\"621\" height=\"568\" src=\"https:\/\/blog.thomarite.uk\/wp-content\/uploads\/2020\/05\/mpls-sr-ceos.png\" alt=\"\" class=\"wp-image-177\" srcset=\"https:\/\/blog.thomarite.uk\/wp-content\/uploads\/2020\/05\/mpls-sr-ceos.png 621w, https:\/\/blog.thomarite.uk\/wp-content\/uploads\/2020\/05\/mpls-sr-ceos-300x274.png 300w\" sizes=\"auto, (max-width: 709px) 85vw, (max-width: 909px) 67vw, (max-width: 984px) 61vw, (max-width: 1362px) 45vw, 600px\" \/><\/figure>\n\n\n\n<p>So what we need and what we are going to use in this lab:<\/p>\n\n\n\n<ul class=\"wp-block-list\"><li>IPv4 (yeah, I should start working in IPv6&#8230;)<\/li><li>IGP: we use ISIS<\/li><li>Label Distribution: ISIS-SR<\/li><li>BGP: using loobacks as best practices and using IGP for building a full-mesh<\/li><li>L3\/2VPN: EVPN<\/li><li>All devices are PE<\/li><\/ul>\n\n\n\n<p>So let&#8217;s build the basic IP  connectivity for r01:<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">!\nhostname r01\n!\ninterface Ethernet1\nno switchport\nip address 10.0.10.1\/30\n!\ninterface Ethernet2\nno switchport\nip address 10.0.12.1\/30\n!\ninterface Loopback1\ndescription CORE Loopback\nip address 10.0.0.1\/32\n!\nip routing\n!<\/pre>\n\n\n\n<p>Now let&#8217;s build our IGP with ISIS. We are going to use our Lo1 IP as network ID for each router. As well, we will keep it simple and define all routers as ISIS L2. We dont need anything fancy. We just want ISIS to build our iBGP peering. We will enable ISIS in the core interfaces (in this simple lab, all links and loopbacks)<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">!\nrouter isis CORE\nnet 49.0000.0001.0010.0000.0000.0001.00  &lt;-- BASED IN Lo1 !!!\nis-type level-2\nlog-adjacency-changes\nset-overload-bit on-startup wait-for-bgp timeout 180\n!\ninterface Ethernet1\nno switchport\nip address 10.0.10.1\/30\nisis enable CORE\nisis metric 40\nisis network point-to-point\n!\ninterface Ethernet2\nno switchport\nip address 10.0.12.1\/30\nisis enable CORE\nisis metric 50\nisis network point-to-point\n!\ninterface Loopback1\ndescription CORE Loopback\nip address 10.0.0.1\/32\nisis enable CORE\nisis metric 1\n!\n<\/pre>\n\n\n\n<p>It is seems there is a bug in the cEOS I am using as &#8220;show isis neighbors&#8221; fails but the routing is actually correct. Let&#8217;s see from r22:<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">r22#show ip route\nVRF: default\nCodes: C - connected, S - static, K - kernel,\nO - OSPF, IA - OSPF inter area, E1 - OSPF external type 1,\nE2 - OSPF external type 2, N1 - OSPF NSSA external type 1,\nN2 - OSPF NSSA external type2, B - BGP, B I - iBGP, B E - eBGP,\nR - RIP, I L1 - IS-IS level 1, I L2 - IS-IS level 2,\nO3 - OSPFv3, A B - BGP Aggregate, A O - OSPF Summary,\nNG - Nexthop Group Static Route, V - VXLAN Control Service,\nDH - DHCP client installed default route, M - Martian,\nDP - Dynamic Policy Route, L - VRF Leaked\nGateway of last resort is not set\nI L2 10.0.0.1\/32 [115\/131] via 10.0.10.9, Ethernet1\nI L2 10.0.0.2\/32 [115\/91] via 10.0.10.9, Ethernet1\nI L2 10.0.0.3\/32 [115\/91] via 10.0.23.1, Ethernet2\nI L2 10.0.0.4\/32 [115\/51] via 10.0.23.1, Ethernet2\nI L2 10.0.0.5\/32 [115\/41] via 10.0.10.9, Ethernet1\nC 10.0.0.6\/32 is directly connected, Loopback1\nI L2 10.0.10.0\/30 [115\/130] via 10.0.10.9, Ethernet1\nI L2 10.0.10.4\/30 [115\/90] via 10.0.23.1, Ethernet2\nC 10.0.10.8\/30 is directly connected, Ethernet1\nI L2 10.0.12.0\/30 [115\/140] via 10.0.23.1, Ethernet2\nI L2 10.0.13.0\/30 [115\/90] via 10.0.10.9, Ethernet1\nC 10.0.23.0\/30 is directly connected, Ethernet2\nr22#\nr22# show logging\n...\nLog Buffer:\nMay 24 16:18:22 r22 SuperServer: %SYS-5-SYSTEM_RESTARTED: System restarted\nMay 24 16:24:29 r22 ConfigAgent: %SYS-5-CONFIG_E: Enter configuration mode from console by root on vty4 (UnknownIpAddr)\nMay 24 16:24:29 r22 ConfigAgent: %SYS-5-CONFIG_I: Configured from console by root on vty4 (UnknownIpAddr)\nMay 24 16:24:29 r22 ConfigAgent: %SYS-5-CONFIG_STARTUP: Startup config saved from system:\/running-config by root on vty4 (UnknownIpAddr).\nMay 24 16:24:39 r22 Isis: %ISIS-4-ISIS_ADJCHG: L2 Neighbor State Change for SystemID 0000.0000.0004 on eth2 to UP\nMay 24 16:24:42 r22 Isis: %ISIS-4-ISIS_ADJCHG: L2 Neighbor State Change for SystemID 0000.0000.0005 on eth1 to UP\nMay 24 16:26:34 r22 ConfigAgent: %SYS-5-CONFIG_STARTUP: Startup config saved from system:\/running-config by root on vty4 (UnknownIpAddr).\nr22#\nr22#show isis neighbors\n% Internal error\n% To see the details of this error, run the command 'show error 2'<\/pre>\n\n\n\n<p>Let&#8217;s build BGP, from r01 is like this:<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">!\nrouter bgp 100\nrouter-id 10.0.0.1\ngraceful-restart restart-time 300\ngraceful-restart\nmaximum-paths 2\nneighbor AS100-CORE peer group\nneighbor AS100-CORE remote-as 100\nneighbor AS100-CORE next-hop-self\nneighbor AS100-CORE update-source Loopback1\nneighbor AS100-CORE timers 2 6\nneighbor AS100-CORE additional-paths receive\nneighbor AS100-CORE additional-paths send any\nneighbor AS100-CORE password 7 Nmg+xbfVkywN7BBIllK5yw==\nneighbor AS100-CORE send-community standard extended\nneighbor AS100-CORE maximum-routes 0\nneighbor 10.0.0.2 peer group AS100-CORE\nneighbor 10.0.0.2 description R02\nneighbor 10.0.0.3 peer group AS100-CORE\nneighbor 10.0.0.3 description R11\nneighbor 10.0.0.4 peer group AS100-CORE\nneighbor 10.0.0.4 description R12\nneighbor 10.0.0.5 peer group AS100-CORE\nneighbor 10.0.0.5 description R21\nneighbor 10.0.0.6 peer group AS100-CORE\nneighbor 10.0.0.6 description R22\n!\n<\/pre>\n\n\n\n<p>So once we have configured BGP in all routers, we should see a full mesh between all routers. This is from r22:<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">r22#show ip bgp summary\nBGP summary information for VRF default\nRouter identifier 10.0.0.6, local AS number 100\nNeighbor Status Codes: m - Under maintenance\nDescription Neighbor V AS MsgRcvd MsgSent InQ OutQ Up\/Down State PfxRcd PfxAcc\nR01 10.0.0.1 4 100 7 7 0 0 00:00:05 Estab 0 0\nR02 10.0.0.2 4 100 7 7 0 0 00:00:05 Estab 0 0\nR11 10.0.0.3 4 100 7 7 0 0 00:00:05 Estab 0 0\nR12 10.0.0.4 4 100 6 7 0 0 00:00:04 Estab 0 0\nR21 10.0.0.5 4 100 6 7 0 0 00:00:04 Estab 0 0\nr22#<\/pre>\n\n\n\n<p>Now, enable MPLS and SR extension in ISIS:<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">!\nmpls ip\n!\nmpls label range isis-sr 800000 65536\n!\nrouter isis CORE\n  segment-routing mpls\n    router-id 10.0.0.1  &lt;-- based on Lo1 in each router\n    no shutdown\n!\ninterface Loopback1\n  description CORE Loopback\n  node-segment ipv4 index 1  &lt;-- this has to be different in each node!!!\n!<\/pre>\n\n\n\n<p>And you should see 5 ISIS-SR tunnels from each router. From r22:<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">r22#show isis segment-routing tunnel\nIndex Endpoint Nexthop Interface Labels TI-LFA\ntunnel index\n\n1 10.0.0.2\/32 10.0.10.9 Ethernet1 [ 800002 ] -\n2 10.0.0.3\/32 10.0.23.1 Ethernet2 [ 800003 ] -\n3 10.0.0.4\/32 10.0.23.1 Ethernet2 [ 3 ] -\n4 10.0.0.5\/32 10.0.10.9 Ethernet1 [ 3 ] -\n5 10.0.0.1\/32 10.0.10.9 Ethernet1 [ 800001 ] -\nr22#<\/pre>\n\n\n\n<p>As you can see above, the labels are based on the base index (800000) defined in the &#8220;mpls label range&#8221; command and the &#8220;node-segment index&#8221; defined in the loopback interface. So the label that identifies uniquely r01 is 800000  + 1 = 800001. The label &#8220;3&#8221; means you are a Penultime-Hop-P router and you remove the label to save a label look-up in the egress router.<\/p>\n\n\n\n<p>Now, let&#8217;s configure EVPN for L2\/L3VPN deployment in our MPLS network. From r01 should be:<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">!\nservice routing protocols model multi-agent --&gt; you will have to reboot\n!\nrouter bgp 100\n!\naddress-family evpn\nneighbor default encapsulation mpls next-hop-self source-interface Loopback1\nneighbor 10.0.0.2 activate\nneighbor 10.0.0.3 activate\nneighbor 10.0.0.4 activate\nneighbor 10.0.0.5 activate\nneighbor 10.0.0.6 activate\n!<\/pre>\n\n\n\n<p>So once this is configured in all routers, we should see again a full mesh of EVPN BGP peers. From r12 this time:<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">r12#show bgp evpn summary\nBGP summary information for VRF default\nRouter identifier 10.0.0.4, local AS number 100\nNeighbor Status Codes: m - Under maintenance\nDescription Neighbor V AS MsgRcvd MsgSent InQ OutQ Up\/Down State PfxRcd PfxAcc\nR01 10.0.0.1 4 100 1254 1251 0 0 00:03:27 Estab 1 1\nR02 10.0.0.2 4 100 1111 1107 0 0 00:03:27 Estab 1 1\nR11 10.0.0.3 4 100 961 962 0 0 00:03:27 Estab 1 1\nR21 10.0.0.5 4 100 884 888 0 0 00:03:27 Estab 1 1\nR22 10.0.0.6 4 100 814 811 0 0 00:03:27 Estab 1 1\nr12#<\/pre>\n\n\n\n<p>Now, let&#8217;s create a L3VPN with CUST-A vrf. We define it in all routers. For r01 should be:<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">!\nvrf instance CUST-A\nrd 100:1\n!\ninterface Loopback2\nvrf CUST-A\nip address 192.168.0.1\/32   &lt;-- each device has a unique one\n!\nip routing vrf CUST-A\n!\nrouter bgp 100\n!\nvrf CUST-A\nrd 100:1\nroute-target import evpn 100:1\nroute-target export evpn 100:1\nnetwork 192.168.0.1\/32<\/pre>\n\n\n\n<p>Let&#8217;s see if the routing works from r12<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">r12#\nr12#show bgp evpn\nBGP routing table information for VRF default\nRouter identifier 10.0.0.4, local AS number 100\nRoute status codes: s - suppressed, * - valid, &gt; - active, # - not installed, E - ECMP head, e - ECMP\nS - Stale, c - Contributing to ECMP, b - backup\n% - Pending BGP convergence\nOrigin codes: i - IGP, e - EGP, ? - incomplete\nAS Path Attributes: Or-ID - Originator ID, C-LST - Cluster List, LL Nexthop - Link Local Nexthop\n<code>Network Next Hop Metric LocPref Weight Path <\/code>\n<code>RD: 100:1 ip-prefix 192.168.0.1\/32 10.0.0.1 - 100 0 i <\/code>\n<code>RD: 100:1 ip-prefix 192.168.0.2\/32 10.0.0.2 - 100 0 i <\/code>\n<code>RD: 100:1 ip-prefix 192.168.0.3\/32 10.0.0.3 - 100 0 i <\/code>\n<code>RD: 100:1 ip-prefix 192.168.0.5\/32 10.0.0.5 - 100 0 i <\/code>\n<code>RD: 100:1 ip-prefix 192.168.0.6\/32 10.0.0.6 - 100 0 i<\/code>\nr12#\nr12#show ip route vrf CUST-A\nVRF: CUST-A\nCodes: C - connected, S - static, K - kernel,\nO - OSPF, IA - OSPF inter area, E1 - OSPF external type 1,\nE2 - OSPF external type 2, N1 - OSPF NSSA external type 1,\nN2 - OSPF NSSA external type2, B - BGP, B I - iBGP, B E - eBGP,\nR - RIP, I L1 - IS-IS level 1, I L2 - IS-IS level 2,\nO3 - OSPFv3, A B - BGP Aggregate, A O - OSPF Summary,\nNG - Nexthop Group Static Route, V - VXLAN Control Service,\nDH - DHCP client installed default route, M - Martian,\nDP - Dynamic Policy Route, L - VRF Leaked\nGateway of last resort is not set\nB I 192.168.0.1\/32 [200\/0] via 10.0.0.1\/32, IS-IS SR tunnel index 5, label 116384\nvia 10.0.10.5, Ethernet1, label 800001\nB I 192.168.0.2\/32 [200\/0] via 10.0.0.2\/32, IS-IS SR tunnel index 2, label 116384\nvia 10.0.10.5, Ethernet1, label 800002\nB I 192.168.0.3\/32 [200\/0] via 10.0.0.3\/32, IS-IS SR tunnel index 3, label 100000\nvia 10.0.10.5, Ethernet1, label imp-null(3)\nC 192.168.0.4\/32 is directly connected, Loopback2\nB I 192.168.0.5\/32 [200\/0] via 10.0.0.5\/32, IS-IS SR tunnel index 4, label 116384\nvia 10.0.23.2, Ethernet2, label 800005\nB I 192.168.0.6\/32 [200\/0] via 10.0.0.6\/32, IS-IS SR tunnel index 1, label 116384\nvia 10.0.23.2, Ethernet2, label imp-null(3)\nr12#<\/pre>\n\n\n\n<p>So, all looks good. EVPN table shows all the prefixes for rd 100:1 and the routing table for CUST-A shows all Lo2 defined in each router.<\/p>\n\n\n\n<p>BTW, I am not able to ping inside the VRF, I think it is something related to the broadcast of ARP:<\/p>\n\n\n\n<p>UPDATE: Arista confirms that cEOS-lab doesn&#8217;t support MPLS dataplane. I need to use vEOS (vagrant). So that means I dont think my laptop has enough resources to build this lab in vEOS \ud83d\ude41<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">r01#ping vrf CUST-A ip 192.168.0.6 interface loopback 2\nPING 192.168.0.6 (192.168.0.6) from 192.168.0.1 lo2: 72(100) bytes of data.\n--- 192.168.0.6 ping statistics ---\n5 packets transmitted, 0 received, 100% packet loss, time 40ms\nr01#\n\n-- from other session in r01 --\n\nr01#bash\nbash-4.2# ip netns exec ns-CUST-A tcpdump -i lo2\ntcpdump: verbose output suppressed, use -v or -vv for full protocol decode\nlistening on lo2, link-type EN10MB (Ethernet), capture size 262144 bytes\n^C12:46:03.324918 02:00:00:00:00:00 (oui Unknown) &gt; Broadcast, ethertype ARP (0x0806), length 42: Request who-has 192.168.0.6 tell 192.168.0.1, length 28\n12:46:04.348750 02:00:00:00:00:00 (oui Unknown) &gt; Broadcast, ethertype ARP (0x0806), length 42: Request who-has 192.168.0.6 tell 192.168.0.1, length 28\n12:46:05.376723 02:00:00:00:00:00 (oui Unknown) &gt; Broadcast, ethertype ARP (0x0806), length 42: Request who-has 192.168.0.6 tell 192.168.0.1, length 28\n3 packets captured\n3 packets received by filter\n0 packets dropped by kernel\nbash-4.2#\n\n-- from other session in r22, we dont see anything --\n\nr22#bash\nbash-4.2# ip netns exec ns-CUST-A tcpdump -i lo2\ntcpdump: verbose output suppressed, use -v or -vv for full protocol decode\nlistening on lo2, link-type EN10MB (Ethernet), capture size 262144 bytes\n^C\n0 packets captured\n0 packets received by filter\n0 packets dropped by kernel\nbash-4.2#<\/pre>\n","protected":false},"excerpt":{"rendered":"<p>We have been able to create some nice MPLS labs using GNS3 and Cisco IOS. In my current employer, we use Arista so I wanted to create a lab environment with Arista kit to simulate a MPLS Segment Routing network. Keeping in mind that I try to run everything on my laptop, using GNS3 + &hellip; <a href=\"https:\/\/blog.thomarite.uk\/index.php\/2020\/05\/25\/mpls-segment-routing-arista-lab\/\" class=\"more-link\">Continue reading<span class=\"screen-reader-text\"> &#8220;MPLS Segment Routing &#8211; Arista Lab&#8221;<\/span><\/a><\/p>\n","protected":false},"author":1,"featured_media":0,"comment_status":"closed","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"footnotes":""},"categories":[2],"tags":[],"class_list":["post-176","post","type-post","status-publish","format-standard","hentry","category-networks"],"_links":{"self":[{"href":"https:\/\/blog.thomarite.uk\/index.php\/wp-json\/wp\/v2\/posts\/176","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/blog.thomarite.uk\/index.php\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/blog.thomarite.uk\/index.php\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/blog.thomarite.uk\/index.php\/wp-json\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/blog.thomarite.uk\/index.php\/wp-json\/wp\/v2\/comments?post=176"}],"version-history":[{"count":5,"href":"https:\/\/blog.thomarite.uk\/index.php\/wp-json\/wp\/v2\/posts\/176\/revisions"}],"predecessor-version":[{"id":235,"href":"https:\/\/blog.thomarite.uk\/index.php\/wp-json\/wp\/v2\/posts\/176\/revisions\/235"}],"wp:attachment":[{"href":"https:\/\/blog.thomarite.uk\/index.php\/wp-json\/wp\/v2\/media?parent=176"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/blog.thomarite.uk\/index.php\/wp-json\/wp\/v2\/categories?post=176"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/blog.thomarite.uk\/index.php\/wp-json\/wp\/v2\/tags?post=176"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}