Sanity check on grouping query
Your query isn't right, and in my opinion, your schema doesn't make sense either.

What is the purpose of the sub-select in your query?  Is your query not equivalent to

SELECT * 
    FROM `translations_urls` AS `t`
    GROUP BY `url_gb`
    ORDER BY iso = 'GB' DESC, `order` ASC, `url_gb` ASC;


Furthermore, what do you intend to achieve with GROUP BY?  You aren't using any aggregate functions in your output columns.  In fact, with a sane database engine (e.g. PostgreSQL), such a query would generate an error like


  ERROR:  column "t.id" must appear in the GROUP BY clause or be used in an aggregate function




Your schema seems awkward to me, for several reasons:


The url_gb column implies that GB is the original language, which, as you stated, is no longer a valid assumption.
The use of url_gb to identify a translation's original results in a normalization problem.  If the URL of a UK-English document changes, you have to update the url_gb of all of its translations.


Furthermore, translations should have language codes, not country codes.  (An exception would be if you were "translating" legal contracts, in which case you want a different document per country.)

One solution is to make a self-referential table that could form a tree of documents:

CREATE TABLE `documents`
( `id` INT(10) UNSIGNED NOT NULL AUTO_INCREMENT
, `order` INT(10) NOT NULL COMMENT 'Sort order'
, `iso` VARCHAR(6) NOT NULL COMMENT 'ISO language code'
, `url` VARCHAR(127) NOT NULL COMMENT 'URL'
, `controller` VARCHAR(127) NOT NULL COMMENT 'Controller the URL refers to'
, `action` VARCHAR(127) NOT NULL COMMENT 'Action the URL refers to'
, `translated_from` INT(10) UNSIGNED COMMENT 'id of document from which this was translated'
, PRIMARY KEY (`id`)
, UNIQUE INDEX `iso_url` (`iso`, `url`)
, FOREIGN KEY (`iso`) REFERENCES `translations_languages` (`iso`)
, FOREIGN KEY (`translated_from`) REFERENCES `documents` (`id`)
)
ENGINE=InnoDB;


Another approach, which I prefer, is to distinguish between documents and their translations.  The advantage of this is that you can nominate one of the translations as the canonical original, to prevent recursion, which is harder to deal with in SQL.

CREATE TABLE `documents`
( `id` INT(10) UNSIGNED NOT NULL AUTO_INCREMENT
, `order` INT(10) NOT NULL COMMENT 'Sort order'
, `canonical` INT(10) UNSIGNED COMMENT 'Canonical (original) translation'
, `controller` VARCHAR(127) NOT NULL COMMENT 'Controller the URL refers to'
, `action` VARCHAR(127) NOT NULL COMMENT 'Action the URL refers to'
, PRIMARY KEY (`id`)
)
ENGINE=InnoDB;

CREATE TABLE `translations`
( `id` INT(10) UNSIGNED NOT NULL AUTO_INCREMENT
, `document_id` INT(10) UNSIGNED NOT NULL
, `iso` VARCHAR(6) NOT NULL COMMENT 'ISO language code'
, `url` VARCHAR(127) NOT NULL COMMENT 'URL'
, PRIMARY KEY (`id`)
, UNIQUE INDEX `document_id_iso` (`document_id`, `iso`)
, UNIQUE INDEX `url` (`url`)
, FOREIGN KEY (`iso`) REFERENCES `translations_languages` (`iso`)
)
ENGINE=InnoDB;

ALTER TABLE `documents`
    ADD FOREIGN KEY (`canonical`) REFERENCES `translations` (`id`);


An annoyance with this schema is the mutual foreign key relationship.  To add a document, you would first have to insert a document with NULL as the canonical translation, then insert the first translation, then update the document with the id of the first translation.



With the latter schema, a query to preferentially return English versions, falling back to a canonical text in another language, would be:

SELECT *
    FROM `documents` AS `d`
        INNER JOIN `translations` AS `t`
            ON `t`.`document_id` = `d`.`id`
    WHERE
        `iso` = 'en' OR
        (`iso` &lt;&gt; 'en' AND `t`.`id` = `d`.`canonical`);