# TeX capacity exceeded while nesting two commands from hyperref and xstring

I have wasted most of my afternoon on this one and can't figure it out. I have prepared an MWE that demonstrates the problem. In my \displaylink command I invoke \href{raw_url}{anchor} (from package hyperref) but I want to build the raw_url with another command, \createurl, which manipulates its argument with one of the xstring utilities.

In the MWE there are two versions of \createurl, one without the command from xstring and one (\createurlx) with it. If you comment out the line labeled "fails", and uncomment the line labelled "works", you see that all three commands (\createurl, \createurlx and \displaylink) work fine. If, however, you comment out the "works" like and uncomment the "fails" line, meaning that from \displaylink you invoke \createurlx which has the call to \StrGobbleLeft from xstring, then things stop working. So it seems to be the nesting of these two commands that's the problem. Why, I have no idea.

BTW my current workaround is that things also work if I put the \StrGobbleLeft inside \displaylink, but I don't want to do that because the \createurlx is a command that's used in other places too. (And of course you realize that these manipulations have been simplified here for the purpose of the MWE---they're somewhat less trivial in the actual document.)

\documentclass{article}
\usepackage{hyperref}
\usepackage{xstring}

\newcommand{\createurl}[1]{
http://www.foobar.com/documents/#1.pdf
}

\newcommand{\createurlx}[1]{
\StrGobbleLeft{#1}{1}[\chopped]
http://www.foobar.com/documents/\chopped.pdf
}

% \href{\createurl{#1}}{\mbox{#1}} % works
\href{\createurlx{#1}}{\mbox{#1}} % fails
}

\begin{document}
The generated url looks like this: \createurl{my-stuff}.
The chopped url looks like this: \createurlx{my-stuff}.
\end{document}


This fails with:

    This is pdfTeX, Version 3.14159265-2.6-1.40.18 (TeX Live 2017/Debian) (preloaded format=pdflatex)
restricted \write18 enabled.
entering extended mode
(./mwe2.tex
LaTeX2e <2017-04-15>
Babel <3.18> and hyphenation patterns for 84 language(s) loaded.
(/usr/share/texlive/texmf-dist/tex/latex/base/article.cls
Document Class: article 2014/09/29 v1.4h Standard LaTeX document class
(/usr/share/texlive/texmf-dist/tex/latex/base/size10.clo))
(/usr/share/texlive/texmf-dist/tex/latex/hyperref/hyperref.sty
(/usr/share/texlive/texmf-dist/tex/generic/oberdiek/hobsub-hyperref.sty
(/usr/share/texlive/texmf-dist/tex/generic/oberdiek/hobsub-generic.sty))
(/usr/share/texlive/texmf-dist/tex/latex/graphics/keyval.sty)
(/usr/share/texlive/texmf-dist/tex/generic/ifxetex/ifxetex.sty)
(/usr/share/texlive/texmf-dist/tex/latex/oberdiek/auxhook.sty)
(/usr/share/texlive/texmf-dist/tex/latex/oberdiek/kvoptions.sty)
(/usr/share/texlive/texmf-dist/tex/latex/hyperref/pd1enc.def)
(/usr/share/texlive/texmf-dist/tex/latex/latexconfig/hyperref.cfg)
(/usr/share/texlive/texmf-dist/tex/latex/url/url.sty))
(/usr/share/texlive/texmf-dist/tex/latex/hyperref/hpdftex.def
(/usr/share/texlive/texmf-dist/tex/latex/oberdiek/rerunfilecheck.sty))
(/usr/share/texlive/texmf-dist/tex/generic/xstring/xstring.sty
(/usr/share/texlive/texmf-dist/tex/generic/xstring/xstring.tex)) (./mwe2.aux)
(/usr/share/texlive/texmf-dist/tex/latex/hyperref/nameref.sty
(/usr/share/texlive/texmf-dist/tex/generic/oberdiek/gettitlestring.sty))
(./mwe2.out) (./mwe2.out)
! TeX capacity exceeded, sorry [input stack size=5000].
\Hy@href {->\hyper@normalise
\href@ {
.
!  ==> Fatal error occurred, no output PDF file produced!
Transcript written on mwe2.log.


EDIT: as @egreg correctly surmises in a comment, this is not the actual string manipulation I need. The actual one requires transforming an input like 2010-x03-y10 into 2010x3y10, that is to say removing the hyphens and any leading zeros---and then adding a constant prefix and suffix. I have had no trouble coding that up as a sequence of xstring operations and storing the result in a command name (the \chopped of my MWE), but I have not been able to "hand the obtained string to \href" (in plain Latex please if possible---but I'm told by @Herbert below that it's not).

• Most of the xstring macros are not expandable and cannot be fed into other macros
– user31729
Jan 2, 2019 at 18:54
• This simple manipulation doesn't seem the real one you need. Complex string manipulations can often only be done in non-expandable way, so they have to be performed before handing the obtained string to \href. Can you please be more detailed about what manipulations you really need? Jan 2, 2019 at 21:23

If no expl3 features are to be used, I suggest to apply \StrGobbleLeft in \displaylink and apply \chopped there. The \StrGobbleLeft macro can still be applied in \createurlx anyway.

\StrGobbleLeft is like almost any of the xstring macros not expandable, since it does 'severe' manipulations ('assignments') of the input strings and has optional arguments -- this is not expandable and can as such not occur in \href.

\documentclass{article}
\usepackage{xstring}
\usepackage{hyperref}

\StrGobbleLeft{#1}{1}[\chopped]%
\href{http://www.foobar.com/documents/\chopped.pdf}{\mbox{#1}}
}

\begin{document}
\end{document}

• Yes, thanks, this works and is basically my current workaround as I described in the third paragraph of my question.
– st01
Jan 2, 2019 at 19:20
• @st01: I know that you described it there -- I suggest it to you as one of the 'easiest' approachest however. Better setups require more information.
– user31729
Jan 2, 2019 at 19:21
• Thanks. It feels broken to have to duplicate the code of \createurl (which is useful on its own) inside \displaylink, with the usual issues of later updating things in one place but not the other, but if what I already have is deemed one of the easiest approaches then I may stick with it.
– st01
Jan 2, 2019 at 19:27

\StrGobbleLeft can not be used in such arguments. If you really only want to remove one char you can use \tl_tail:n from expl3, this is expandable:

\documentclass{article}
\usepackage{hyperref}
\usepackage{expl3}

\newcommand{\createurl}[1]{
http://www.foobar.com/documents/#1.pdf
}

\ExplSyntaxOn
\newcommand{\createurlx}[1]
{
http://www.foobar.com/documents/\tl_tail:n{#1}.pdf
}

\ExplSyntaxOff

\href{\createurlx{#1}}{\mbox{#1}}%
}

\begin{document}
The generated url looks like this: \createurl{my-stuff}.
The chopped url looks like this: \createurlx{my-stuff}.
\end{document}

• There is a % missing in \createurl (It's not really important, because that command is not used most likely)
– user31729
Jan 2, 2019 at 19:05
• No, unfortunately \StrGobbleLeft was only used as a MWE placeholder for a bunch of xstring-related manipulations that I need to do to create the url. What's the reason the xstring macros cannot be used in such arguments, and how could I have guessed that from the obscure "TeX capacity exceeded" error message?
– st01
Jan 2, 2019 at 19:12
• \href wants to manipulate tokens too. Change your url before the \href (check the regex-commands of expl3 too) and fed a simple macro to the \href. Be careful with special chars like ~ or #. Jan 2, 2019 at 19:16
\documentclass[a4paper]{article}
\usepackage[margin=1cm]{geometry}
\usepackage{hyperref}

\newcommand{\createurl}[1]{%
http://www.foobar.com/documents/#1.pdf%
}
\newcommand\createurlx[1]{\createURLX#1!!}
\def\createURLX#1#2!!{%
http://www.foobar.com/documents/#2.pdf%
}
\href{\createurlx{#1}}{\mbox{#1}}%
}

\begin{document}
The generated url looks like this: \createurl{my-stuff}.

The chopped url looks like this: \createurlx{my-stuff}.

\end{document}

• Wow! Thanks! It works, but I have no idea how or why ;-) What do the exclamation marks do? Care to enlighten me?
– st01
Jan 2, 2019 at 19:15
• \createURLX#1!! has the two !! to define the end of the string. You can choose any character which will not be part of the url. \def\createURLX#1#2!! uses #1 as the first character (token) in the input and #2 everything else until the !!
– user2478
Jan 2, 2019 at 19:19
• Both of these explanations are somewhat on the terse side and I need to understand a bit more about this if I am going to port this to my non-minimal piece of code. I am leafing through the latex book but can't find a mention of this: where should I be looking?
– st01
Jan 2, 2019 at 19:25
• That is no LaTeX magic but TeX magic and ctan.org/pkg/texbytopic?lang=de maybe a good starter. It cannot be learned in a couple of minutes ;-)
– user2478
Jan 2, 2019 at 19:27
• in LaTeX3 yes, but not really in the current LaTeX2e
– user2478
Jan 2, 2019 at 19:29