Extract numbers from the head of a string in BASH script
bash is slow to append and index into strings: both operations are \$O(n)\$.  Your approach does as many indexes and appends as there are digits in the input, making it \$O(n^2)\$.  And processing a string by chomping the first character repeatedly will be \$O(n^2)\$ in almost every language.  

Have a look at these timings for large inputs, using your code:

$ for x in 10000 20000 40000 80000; do echo $x; time bash dig.sh $( tr -dc 0-9 &lt; /dev/urandom | head -c $x ) &gt;/dev/null ; done

input size (1000's of digits)  runtime (seconds)
         10                      1.1 
         20                      4.4
         40                     17.7
         80                     71.6


Almost perfectly quadratic!  It's possible to do better, and in fewer lines.   

Your code is implementing a state machine, just like a regular expression would, but much less efficiently.  So the regex isn't needless overhead; it's very necessary  (and profitable) "underhead":

dig() { 
    [[ $1 =~ ^([0-9,]*)(.*) ]] # this always matches
    digits="${BASH_REMATCH[1]//,}"
    remain="${BASH_REMATCH[2]}"
    printf "input\t'%s'\tdigits\t'%s'\tremain\t'%s'\n" "$1" "$digits" "$remain"
}




+ dig ''
input   ''      digits  ''      remain  ''
+ dig 1234
input   '1234'  digits  '1234'  remain  ''
+ dig 1,234
input   '1,234' digits  '1234'  remain  ''
+ dig abc12
input   'abc12' digits  ''      remain  'abc12'
+ dig 12z34
input   '12z34' digits  '12'    remain  'z34'




$ for x in 10000 20000 40000 80000; do echo $x; time dig $( tr -dc 0-9 &lt; /dev/urandom | head -c $x ) &gt;/dev/null ; done

input size (1000's of digits)  runtime (seconds)
         10                      0.006 
         20                      0.010
         40                      0.018
         80                      0.032


Behold: a two-thousand-fold speedup of the slowest case!