```ts
export function parseSpan(text: string): number {
  if (typeof text !== 'string' || !text.trim()) throw new Error('Invalid span');

  const parts = text.split(/\s+/);
  const units = ['yd', 'ft', 'in'];
  let totalInches = 0;

  for (let i = 0; i < parts.length; i++) {
    const part = parts[i];
    if (!part) throw new Error('Invalid span');

    const match = part.match(/^(\d+)([a-z]{2})$/);
    if (!match) throw new Error('Invalid span');

    const value = parseInt(match[1], 10);
    const unit = match[2];

    if (isNaN(value) || value < 0 || !units.includes(unit)) throw new Error('Invalid span');
    if (i > 0 && units.indexOf(unit) <= units.indexOf(parts[i - 1].match(/[a-z]{2}$/)[0])) throw new Error('Invalid span');

    switch (unit) {
      case 'yd': totalInches += value * 36; break;
      case 'ft': totalInches += value * 12; break;
      case 'in': totalInches += value; break;
    }
  }

  return totalInches;
}

export function formatSpan(inches: number): string {
  if (typeof inches !== 'number' || !Number.isInteger(inches) || inches < 0) throw new Error('Invalid inches');

  let result = '';
  const yards = Math.floor(inches / 36);
  inches %= 36;
  const feet = Math.floor(inches / 12);
  inches %= 12;

  if (yards > 0) result += `${yards}yd `;
  if (feet > 0) result += `${feet}ft `;
  if (inches > 0) result += `${inches}in`;

  return result.trim() || '0in';
}

export function addSpans(first: string, second: string): string {
  const totalInches = parseSpan(first) + parseSpan(second);
  return formatSpan(totalInches);
}
```