stringtypescriptlogical-or

TypeScript's type 'string | string[]' is not assignable to type 'string', what is the 'string | string[]' type? How to cast them to string?


When I do TypeScript:

let token = req.headers['x-access-token'] || req.headers['authorization'] as string;

I have the following error:

Argument of type 'string | string[]' is not assignable to parameter of type 'string'

Does anyone know what string | string[] type is? I mean if I want to use logical 'or' of two strings in TypeScript. How to do it?

And how to cast string | string[] to string type?


Solution

  • I guess you are using node.js. In this case req.headers is of type IncomingHttpHeaders which has an index-signature of: [header: string]: string | string[] | undefined;
    That means, that req.headers['whatever'] can be of type string or string[] (array of string) or undefined

    Hint
    instead of req.headers['authorization'] you can use req.headers.authorization which is of type string | undefined.

    interface IncomingHttpHeaders {
        .. 
        'authorization'?: string;
        ..
        [header: string]: string | string[] | undefined;
    }
    

    Details
    Note: the answer of Adrian Brand is fine and you can use it as is. For the sake of completion I'll just show a detailed way how you could handle all cases and explain the types:

    const tokenValue= req.headers['x-access-token'] || req.headers['authorization'];
    

    tokenValue is of type string | string[] | undefined.
    Note, that it can also be undefined when none of the headers exist.
    We could handle this case:

    if (!tokenValue) throw Error('missing header')
    

    After this check typescript is smart enough to know that tokenValue is now of type string | string[]

    if (Array.isArray(tokenValue)) {
      // In this if branch the type of `tokenValue` is `string[]`
    } else {
      // In this if branch, the type of `tokenValue` is `string`
    }