public function build($name, Request $request)
    {
        $ret = $this->factory->createItem($name);

        $menus = $this->loadRoots($request);

        if (!isset($menus[$name])) {
            return $ret;
        }

        $requestLocale = $request->get('_locale');

        if (!isset($this->menus[$requestLocale][$name])) {
            $rootIdToNameMap = array_combine(array_column($menus, 0), array_keys($menus));

            if (in_array($name, $this->preloadMenus)) {
                $menusToLoad = [];
                foreach ($this->preloadMenus as $preloadMenuName) {
                    if (!isset($menus[$preloadMenuName])) {
                        continue;
                    }

                    $menusToLoad[$preloadMenuName] = $menus[$preloadMenuName];
                }
            } else {
                $menusToLoad[$name] = $menus[$name];
            }

            $query = 'SELECT root, menu_item.* FROM menu_item WHERE ';
            $i = 0;
            // `$vals` contains [id, lft, rgt]
            foreach ($menusToLoad as $vals) {
                if ($i ++ > 0) {
                    $query .= ' OR ';
                }
                $query .= vsprintf('(root=%d AND lft BETWEEN %d AND %d AND id <> root)', $vals);
            }
            $query .= ' ORDER BY root, lft';

            foreach ($this->em->getConnection()->query($query)->fetchAll(\PDO::FETCH_GROUP) as $rootId => $menu) {
                if (!isset($rootIdToNameMap)) {
                    continue;
                }
                $menuName = $rootIdToNameMap[$rootId];
                $this->menus[$requestLocale][$menuName]= $this->factory->createItem($menuName);

                $this->addMenuItemHierarchy(
                    $request,
                    $this->menuItemEntity->buildTree($menu),
                    $this->menus[$requestLocale][$menuName]
                );
            }
        }

        if (isset($this->menus[$requestLocale][$name])) {
            $ret = $this->menus[$requestLocale][$name];

            if (is_callable([$ret, 'setCurrentUri'])) {
                $ret->setCurrentUri($request->getRequestUri());
            }
        }

        return $ret;
    }