does this work for you?
im assuming what u want to achieve was to flatten error result as normal emit, while still able to specify it to retry on error by the consumer
function getFoo$(retry = false) {
const foo$ = source$.pipe(
catchError((error) => {
const optionalPipes = []
if(retry) optionalPipes.push(mergeMap(() => source$))
return of({ data: null, error}).pipe(...optionalPipes)
}),
)
return foo$
}