Estonia (EUR€) Bearing Cassette Disc hub 36H cog NOT included White","public_title":"T2 26 Rear SS HG Single Speed HG Sealed Bearing Cassette Disc hub 36H cog NOT included White","options":["T2 26 Rear SS HG Single Speed HG Sealed Bearing Cassette Disc hub 36H cog NOT included White"],"price":15999,"weight":0,"compare_at_price":null,"inventory_management":"shopify","barcode":null,"featured_media":{"alt":null,"id":31721009381602,"position":2,"preview_image":{"aspect_ratio":1.093,"height":1070,"width":1170,"src":"\/\/projektride.co.uk\/cdn\/shop\/products\/Screenshot2023-03-26at11.56.51.png?v=1679828216"}},"requires_selling_plan":false,"selling_plan_allocations":[],"quantity_rule":{"min":1,"max":null,"increment":1}},{"id":43981392838882,"title":"T2 26 Front Halo SB Black Disc Hub 32H (15mm) Black","option1":"T2 26 Front Halo SB Black Disc Hub 32H (15mm) Black","option2":null,"option3":null,"sku":"WHHA26KF","requires_shipping":true,"taxable":true,"featured_image":{"id":39122260525282,"product_id":8063305187554,"position":3,"cr
Rear Halo SB Black Disc Hub 36H Shimano HG Black","option2":null,"option3":null,"sku":"WHHA26KR","requires_shipping":true,"taxable":true,"featured_image":{"id":39122261278946,"product_id":8063305187554,"position":4,"created_at":"2023-03-26T11:57:31+01:00","updated_at":"2023-03-26T11:57:31+01:00","alt":null,"width":1170,"height":1116,"src":"\/\/projektride.co.uk\/cdn\/shop\/products\/Screenshot2023-03-26at11.57.26.png?v=1679828251","variant_ids":[43981392871650]},"available":true,"name":"Halo T2 26\" Wheels - T2 26 Rear Halo SB Black Disc Hub 36H Shimano HG Black","public_title":"T2 26 Rear Halo SB Black Disc Hub 36H Shimano HG Black","options":["T2 26 Rear Halo SB Black Disc Hub 36H Shimano HG Black"],"price":15999,"weight":0,"compare_at_price":null,"inventory_management":"shopify","barcode":null,"featured_media":{"alt":null,"id":31721010561250,"position":4,"preview_image":{"aspect_ratio":1.048,"height":1116,"width":1170,"src":"\/\/projektride.co.uk\/cdn\/shop\/products\/Screenshot2023-03-26at11.57.26.png?v=
Search0,"compare_at_price":null,"inventory_management":"shopify","barcode":null,"featured_media":{"alt":null,"id":31721011282146,"position":5,"preview_image":{"aspect_ratio":1.048,"height":1116,"width":1170,"src":"\/\/projektride.co.uk\/cdn\/shop\/products\/Screenshot2023-03-26at11.57.47.png?v=1679828271"}},"requires_selling_plan":false,"selling_plan_allocations":[],"quantity_rule":{"min":1,"max":null,"increment":1}},{"id":43981392937186,"title":"T2 26 Disc Rear Disc Rim on Halo SB Black Disc Hub 36H Shimano HG White","option1":"T2 26 Disc Rear Disc Rim on Halo SB Black Disc Hub 36H Shimano HG White","option2":null,"option3":null,"sku":"WHHA26WKR","requires_shipping":true,"taxable":true,"featured_image":{"id":39122262196450,"product_id":8063305187554,"position":6,"created_at":"2023-03-26T11:57:58+01:00","updated_at":"2023-03-26T11:57:58+01:00","alt":null,"width":1170,"height":1116,"src":"\/\/projektride.co.uk\/cdn\/shop\/products\/Screenshot2023-03-26at11.57.53.png?v=1679828278","variant_ids":[43981392937186]},"avaCameroon (XAFCFA) /\/projektride.co.uk\/cdn\/shop\/products\/Screenshot2023-03-26at11.57.26.png?v=1679828251","\/\/projektride.co.uk\/cdn\/shop\/products\/Screenshot2023-03-26at11.57.47.png?v=1679828271","\/\/projektride.co.uk\/cdn\/shop\/products\/Screenshot2023-03-26at11.57.53.png?v=1679828278"],"featured_image":"\/\/projektride.co.uk\/cdn\/shop\/products\/Screenshot2023-03-26at11.56.36.png?v=1679828201","options":["Size"],"media":[{"alt":null,"id":31721008857314,"position":1,"preview_image":{"aspect_ratio":1.093,"height":1070,"width":1170,"src":"\/\/projektride.co.uk\/cdn\/shop\/products\/Screenshot2023-03-26at11.56.36.png?v=1679828201"},"aspect_ratio":1.093,"height":1070,"media_type":"image","src":"\/\/projektride.co.uk\/cdn\/shop\/products\/Screenshot2023-03-26at11.56.36.png?v=1679828201","width":1170},{"alt":null,"id":31721009381602,"position":2,"preview_image":{"aspect_ratio":1.093,"height":1070,"width":1170,"src":"\/\/projektride.co.uk\/cdn\/shop\/products\/Screenshot2023-03-26at11.56.51.png?v=1679828216"},"aspect_rati
Eswatini (GBP£) :1170,"src":"\/\/projektride.co.uk\/cdn\/shop\/products\/Screenshot2023-03-26at11.57.47.png?v=1679828271"},"aspect_ratio":1.048,"height":1116,"media_type":"image","src":"\/\/projektride.co.uk\/cdn\/shop\/products\/Screenshot2023-03-26at11.57.47.png?v=1679828271","width":1170},{"alt":null,"id":31721011478754,"position":6,"preview_image":{"aspect_ratio":1.048,"height":1116,"width":1170,"src":"\/\/projektride.co.uk\/cdn\/shop\/products\/Screenshot2023-03-26at11.57.53.png?v=1679828278"},"aspect_ratio":1.048,"height":1116,"media_type":"image","src":"\/\/projektride.co.uk\/cdn\/shop\/products\/Screenshot2023-03-26at11.57.53.png?v=1679828278","width":1170}],"requires_selling_plan":false,"selling_plan_groups":[],"content":"\u003cmeta charset=\"utf-8\"\u003e\n\u003cdiv class=\"col-md-8\"\u003e\n\u003cp\u003eMiddleweight multi-purpose 26\" MTB wheels.\u003c\/p\u003e\n\u003cp\u003eLight and strong, angular style box section rim, with eyelets and a stable screw-pin joint.\u003c\/p\u003e\n\u003cp\u003eThe front wheel feat Header Image e\u003cspan class=\"ui-list-info\"\u003e100 x 15mm thru\u003c\/span\u003e\n\u003c\/li\u003e\n\u003cli class=\"ui-list_item\"\u003e\n\u003cspan class=\"ui-list-title\"\u003eRear 135\u003c\/span\u003e\u003cspan class=\"ui-list-info\"\u003e135 x 9mm QR\u003c\/span\u003e\n\u003c\/li\u003e\n\u003c\/ul\u003e\n\u003ch4\u003eSpecifications\u003c\/h4\u003e\n\u003cul class=\"ui-list ui-list-main\"\u003e\n\u003cli class=\"ui-list_item\"\u003e\n\u003cspan class=\"ui-list-title\"\u003eRims: \u003c\/span\u003e\u003cspan class=\"ui-list-info\"\u003eHalo 32mm T2 rims with eyelets\u003c\/span\u003e\n\u003c\/li\u003e\n\u003cli class=\"ui-list_item\"\u003e\n\u003cspan class=\"ui-list-title\"\u003eHubs: \u003c\/span\u003e\u003cspan class=\"ui-list-info\"\u003eHalo MT Series hubs\u003c\/span\u003e\n\u003c\/li\u003e\n\u003cli class=\"ui-list_item\"\u003e\n\u003cspan class=\"ui-list-title\"\u003eExternal Rim Width: \u003c\/span\u003e\u003cspan class=\"ui-list-info\"\u003e32mm\u003c\/span\u003e\n\u003c\/li\u003e\n\u003cli class=\
itle\"\u003eFreehub Body: \u003c\/span\u003e\u003cspan class=\"ui-list-info\"\u003eShimano HG compatible\u003c\/span\u003e\n\u003c\/li\u003e\n\u003cli class=\"ui-list_item\"\u003e\n\u003cspan class=\"ui-list-title\"\u003eSpoke lengths: \u003c\/span\u003e\u003cspan class=\"ui-list-info\"\u003e258mm (front), 256\/254mm (rear)\u003c\/span\u003e\n\u003c\/li\u003e\n\u003cli class=\"ui-list_item\"\u003e\n\u003cspan class=\"ui-list-title\"\u003eSpoke pattern: \u003c\/span\u003e\u003cspan class=\"ui-list-info\"\u003eRace optimised 36H rear \u0026amp; 32H front spoking\u003c\/span\u003e\n\u003c\/li\u003e\n\u003cli class=\"ui-list_item\"\u003e\n\u003cspan class=\"ui-list-title\"\u003eBearings: \u003c\/span\u003e\u003cspan class=\"ui-list-info\"\u003e6804 (front), 6200\/6000 (rear) cartridge bearings\u003c\/span\u003e\n\u003c\/li\u003e\n\u003cli class=\"ui-list_item\"\u003e\n\u003cspan class=\"ui-list-title\"\u003eTubeless: \u003c\/span\u003e\u003cspan class=\"ui-list-info\"\u003eNo\u003c\/span\u003e\n\u003c\/li\u0Cape Verde (CVE$) nt(""),43981392904418 : parseInt(""),43981392937186 : parseInt(""),}; window._RestockRocketConfig.variantsPreorderCountForMarket = {43981392773346 : null,43981392806114 : null,43981392838882 : null,43981392871650 : null,43981392904418 : null,43981392937186 : null,}; window._RestockRocketConfig.variantsPreorderMaxCount = {43981392773346 : parseInt(""),43981392806114 : parseInt(""),43981392838882 : parseInt(""),43981392871650 : parseInt(""),43981392904418 : parseInt(""),43981392937186 : parseInt(""),}; window._RestockRocketConfig.variantsPreorderMaxCountForMarket = {43981392773346 : null,43981392806114 : null,43981392838882 : null,43981392871650 : null,43981392904418 : null,43981392937186 : null,}; window._RestockRocketConfig.variantsShippingText = {43981392773346 : "",43981392806114 : "",43981392838882 : "",43981392871650 : "",43981392904418 : "",43981392937186 : "",}; window._RestockRocketConfig.variantsShippingTextForMarket = {43981392773346 : null,43981392806114 : null,43981392838882 : n
Ethiopia (ETBBr) var _sqPreCount = ((_sqCfg.cachedPreorderVariantIds && _sqCfg.cachedPreorderVariantIds.preorder_variant_ids) || []).length; _sqCfg.preordersConfigured = !!(_sqPlanEnabled && _sqPreCount); } catch (e) { /* fail open */ } // STOQ-1612: block (not hide) Buy Now / Shop Pay until our JS runs, so a tap in the // load window can't bypass preorder. pointer-events via .stoq-buy-now-pending (no // reflow); timeout releases; renderPreorderButton / featured_product.js lift it. // Gated by the `block_accelerated_checkout` toggle (default OFF) for gradual rollout. // Armed ONLY when we're sure preorder is in play — product page: THIS product has a // preorder variant (never block a plain product's Shop Pay); featured: integration // enabled for this page type. Rationale: PR #2784. try { var _sqc = window._RestockRocketConfig; var _sqOn = !!(_sqc.cachedSettings && _sqc.cachedSettings.block_accelerated_checkout); var _sqPre = (_sqc.cachedPreorderVariantIds && _sqc.cachedPreo
Cartsets/restockrocket-product.js' window._RestockRocketConfig.scriptUrlCollection = 'https://cdn.shopify.com/extensions/019faf5b-94c9-7a24-9306-bf1118ca3099/restockrocket-1-554/assets/restockrocket-collection.js' window._RestockRocketConfig.scriptUrlProductBis = 'https://cdn.shopify.com/extensions/019faf5b-94c9-7a24-9306-bf1118ca3099/restockrocket-1-554/assets/restockrocket-product-bis.js' window._RestockRocketConfig.scriptUrlCollectionBis = 'https://cdn.shopify.com/extensions/019faf5b-94c9-7a24-9306-bf1118ca3099/restockrocket-1-554/assets/restockrocket-collection-bis.js' window._RestockRocketConfig.scriptHost = window._RestockRocketConfig.scriptUrlProduct.substring(0, window._RestockRocketConfig.scriptUrlProduct.lastIndexOf('/') + 1) // Canary override (STOQ-1287): prefer the Render host emitted into the // metafield-cached settings (api_host) when present, mirroring the same // override in assets/js/api.js. cachedSettings is populated above. Falls // back to the build-baked host for shops witho che age if (!liquidRenderedAt || typeof liquidRenderedAt !== 'number' || isNaN(liquidRenderedAt)) { console.debug('STOQ - Invalid or missing liquidRenderedAt timestamp, assuming fresh'); window._RestockRocketConfig.isLiquidCacheFresh = true; window._RestockRocketConfig.liquidCacheAge = null; } else { const now = Math.floor(Date.now() / 1000); // Current time in seconds const liquidCacheAge = now - liquidRenderedAt; // Age in seconds // Surfaced into funnel events: a stale cache means the app rendered with // outdated inventory/selling-plan data — a real "had the opportunity but // failed" cause. Negative (client clock ahead) clamps to 0. window._RestockRocketConfig.liquidCacheAge = Math.max(0, liquidCacheAge); // Handle client clock ahead of server if (liquidCacheAge
0) { console.debug(`STOQ - Client clock appears ahead of server by ${Math.abs(Math.round(liquidCacheAge / 60))} minutes, assuming cache fresh`); window._RestockRocketConfig.isLiquidCacheFresh = true; } else if (liquidCacheAge Chad (XAFCFA) = LIQUID_CACHE_MAX_AGE) { console.debug(`STOQ - Liquid cache is fresh (${Math.round(liquidCacheAge / 60)} minutes old)`); window._RestockRocketConfig.isLiquidCacheFresh = true; } else { console.debug(`STOQ - Liquid cache is stale (${Math.round(liquidCacheAge / 60)} minutes old, max ${Math.round(LIQUID_CACHE_MAX_AGE / 60)} minutes)`); window._RestockRocketConfig.isLiquidCacheFresh = false; } } function checkSettingsExpiry(settings) { try { if (!settings || !settings.updated_at) { console.debug('STOQ - Invalid settings data structure'); return null; } if (!settings.cache) { console.debug('STOQ - settings caching disabled'); return null; } // Check if translations are enabled but missing from cache // This handles the backfill period where DB has translations but metafield doesn't if (settings.multi_language_enabled) { if (!settings.translations) { // Translations enabled but no
Finland (EUR€) age = Date.now() - updatedAt.getTime(); if (age French Southern Territories (EUR€) version>/graphql.json — never // CDN-cached — so it returns the live value on every page load. We fetch it // best-effort and stash it on `window._RestockRocketConfig.storefrontSettings` // so individual behaviours can migrate onto the fresh value over time. This is // PURELY ADDITIVE: it does NOT change the resolution flow below, never blocks // init, and silently no-ops on any failure / missing token. (function loadStorefrontSettings() { const cfg = window._RestockRocketConfig; if (!cfg.storefrontAccessToken || cfg.disableStorefrontApi === true) return; // Deferred to browser idle so this best-effort read runs strictly AFTER the // critical init flow and never competes with it for a connection — the call // is a live, uncached Storefront round-trip and can be slow (multi-second // TTFB observed). Nothing on the critical path waits for it. function run() { const query = 'query StoqSettings($namespace: String!) { shop { metafield(namespace: $namespace, key:
refrontSettings = JSON.parse(value); console.debug('STOQ - stored live settings from Storefront API on config.storefrontSetting
s'); }) .catch(function(e) { console.debug('STOQ - Storefront settings fetch failed (non-fatal):', e && e.message); }); } if (typeof window.requestIdleCallback === 'function') { window.requestIdleCallback(run, { timeout: 5000 }); } else { setTimeout(run, 0); } })(); // First try to get settings from metafields with expiry check const cachedSettings = window._RestockRocketConfig.cachedSettings; const validCachedSettings = cachedSettings ? checkSettingsExpiry(cachedSettings) : null; if (validCachedSettings) { console.debug('STOQ - using cached settings'); initializeScripts(validCachedSettings); } else { console.debug('STOQ - fetching fresh settings'); const headers = { 'X-Shopify-Shop-Domain': window._RestockRocketConfig.shop || window.Shopify.shop, 'ngrok-skip-browser-warning': 'skip' }; if (window.Shopify?.theme?.role === 'main') { headers['X-Shopify-Theme-Schema-Name'] = window.Shopify.theme.schema Congo - Kinshasa (CDFFr) _name; headers['X-Shopify-Theme-Schema-Version'] = window.Shopify.theme.schema_version; headers['X-Shopify-Theme-Store-Id'] = window.Shopify.theme.theme_store_id; } fetch( `${window._RestockRocketConfig.host}/api/v1/setting.json?translation_locale=${window._RestockRocketConfig.normalizedLocale}`, { headers } ) .then(function(response) { if (!response.ok) { throw new Error('Network response was not ok'); } return response.json(); }) .then(function(settings) { initializeScripts(settings); }) .catch(function(error) { // If request failed and we have cached settings (even if expired), use them as fallback if (cachedSettings) { console.debug('STOQ - using expired cached settings as fallback'); initializeScripts(cachedSettings); } else { console.error('STOQ - failed to load settings:', error); } }) .catch(function(e) { console.error(e) }) } function fetchEmb
edConfig(endpoint, apply) { return fetch( `${window._RestockRocketConfig.host}/api/v1/embed/${endpoint}.json`, { headers: { 'X-Shopify-Shop-Domain': window._RestockRocketConfig.shop || window.Shopify.shop, 'ngrok-skip-browser-warning': 'skip' } } ) .then(function(response) { if (!response.ok) throw new Error(`Failed to fetch ${endpoint}`); return response.json(); }) .then(function(data) { try { apply(data); } catch (applyError) { // Apply failures are programming bugs (e.g. response shape changed // server-side and the assignment threw). Surface them as console.error // so they're visible in browser logs, then re-throw to fall through // to the same Liquid-cached fallback as a fetch failure. console.error('STOQ - apply failed for ' + endpoint + ':', applyError); throw applyError; } }) .catch(function(error) { console.debug(`STOQ - using c ached ${endpoint}:`, error.message); }); } function initializeScripts(settings) { settings = applyTranslations(settings); window._RestockRocketConfig.settings = settings; console.debug(`STOQ - settings configured for ${window._RestockRocketConfig.pageType}`); // Stale-Liquid resilience (default-on, per-shop opt-out via the // `disable_refresh_on_stale_liquid` Toggle, surfaced as the negative // `disable_refresh_on_stale_liquid` flag in settings.json so that // `undefined` -- in CDN-cached metafield payloads that predate this // key -- reads as `!undefined === true` and gets default-on behavior // immediately, no metafield rewrite required). // When the Liquid CDN cache is older than LIQUID_CACHE_MAX_AGE the in-page // selling_plans / integrations metafields can be wrong; refresh both from // the API before launching scripts. Race against a 1000ms timeout so a slow // API can't block init indefinitely. If the timeout wins, the in-flight // fetch
es still complete and update window._RestockRocketConfig — the // bundle re-reads sellingPlans/integrations on every interaction, so the // late-arriving values benefit subsequent renders even though the first // paint may use the Liquid-cached values. On any failure the existing // Liquid-loaded values stay in place via fetchEmbedConfig's catch. if (!window._RestockRocketConfig.isLiquidCacheFresh && !settings.disable_refresh_on_stale_liquid) { console.debug('STOQ - Liquid cache stale, refreshing selling_plans + integrations'); Promise.race([ Promise.all([ fetchEmbedConfig('selling_plans', function(data) { if (data && Array.isArray(data.plans)) { window._RestockRocketConfig.sellingPlans = data.plans; window._RestockRocketConfig.disabledSellingPlanIds = data.disabled_plan_ids || []; } }), fetchEmbedConfig('integrations', function(data) { if (Array.isArray(data)) { Gabon (XOFFr) Add order notes window._RestockRocketConfig.integrations = data; } }) ]), new Promise(function(resolve) { setTimeout(resolve, 1000); }) ]).then(function() { loadScripts(settings); }); return; } loadScripts(settings); } function loadScripts(settings) { // Setup cart selling plan updater BEFORE loading any scripts to avoid race conditions setupCartSellingPlanUpdater(settings); if(settings.enable_app) { const hijackIntegration = window._RestockRocketConfig.integrations.find(function(integration) { return integration.type === 'hijack' && integration.enabled && integration.page_types.includes(window._RestockRocketConfig.pageType); }) // STOQ-1520: serve the lean back-in-stock-only build (no preorder/hijack code) // only to shops with NO preorder plans. Use the full build if preorder is on, // an enabled offer exists, or a disabled-but-kept plan id remains (cart sweep // must still strip those). Rationale in
Egypt (EGPج.م)

Surly Nice Rack - Front Eritrea (GBP£)

Open cartItaly (EUR€)
Moldova (MDLL) Monaco (EUR€) HireKosovo (EUR€)
Liechtenstein (CHFCHF)
Electric Bikes Niger (XOFFr) Nigeria (NGN₦) Luxembourg (EUR€) Shop by Brand
North Macedonia (MKDден)
Gloria Madagascar (GBP£)
Trek Norway (GBP£)
Malawi (MWKMK) Poland (PLNzł)
YetiMali (XOFFr)

 

Portugal (EUR€)

Surly Racks are well-thought-out, durable, expedition-worthy racks that work with most panniers. While their racks aren’t limited solely to heavy duty touring, that is what they were designed for.Ridgeback

Malta (EUR€)

When you’re out on the road, the best option is to never ever have anything ever go wrong ever. Right? That’s never a guarantee though; so having something that you can repair if it does brake can be pretty clutch. Thusly, the main bodies of Surly's front and rear racks are made from tubular CroMoly steel with stainless hardware. This means you can probably find someone out there that can torch it back into one piece in the rare instance things go south.

Brother Réunion (EUR€)

The front Rack is height adjustable and provides either a low or high pannier mounting position, which can be handy depending on terrain. When the ground gets rough, keep your gear high and dry. When the path is smooth and easy, you can load things low and keep everything balanced and stable, with the platform above the wheel providing yet more space for more stuff. It’s worth mentioning the Front Rack hardware has been redesigned to be simpler to attach and more compatible with things like disc calipers and fenders. Surly have also made attachment plates specifically for our Uni-Crown forks for yet more fork compatibility. This simpler design has fewer moving parts and costs less to manufacture, ergo costs less for you to purchase.

Mauritania (GBP£)

The Surly front rackGenesis   Romania (RONLei) WILL  SingularMauritius (MUR₨) work with disc brakes on our Troll, Ogre, and Disc Trucker frames. It may take a bit of work to get clearance around the front caliper since the many different calipers out there are many different shapes. The new attachment plates will limit any DIY ingenuity you might need, but if you need to throw a washer or three behind the lower left bolt where the plate attaches to the fork dropout, that’s not a big deal.

Rwanda (RWFFRw)

Front Rack specifications:Enigma

Mayotte (EUR€)
  • Tubing diameter: 10mmFrog San Marino (EUR€)
  • Platform dimensions: 230 x 170mm Moldova (MDLL)
  • Kona
  • Weight: 1382g São Tomé & Príncipe (STDDb)
Senegal (XOFFr)
UTO (ex Eovolt)
Morocco (MADد.م.)
Argon 18
Seychelles (GBP£)

Frequently Asked Questions Second-Hand Bikes

Mozambique (GBP£)
Shop All Second-Hand
  • Custom Builds Custom Builds for sale
    Slovakia (EUR€)

    Please get in touch with a member of the team either by phone ( 01313745324Custom Build Inspiration Netherlands (EUR€) ) or email ( [email protected] Slovenia (EUR€) ) where on of the team will be more than happy to help.

    ProjektRide Bike Shop EdinburghNiger (XOFFr)

    Somalia (GBP£)
  • South Africa (GBP£)

    If the item is showing in stock, we aim to post the product within 24 hours. Please allow 5 working days to receive the item. Workshop

    Postage is free on orders over £50. Orders under £50, our postage charge is £3.99.North Macedonia (MKDден)

    We also have a physical store, if you are local please pop in - Workshop Prices

    ProjektRide Bike Shop Edinburgh South Sudan (GBP£)

    82 Newington Road, EH91QN, Edinburgh.

    Norway (GBP£) Book a Service
Spain (EUR€)
Track Your Service
Poland (PLNzł)