#help with a indexing type

15 messages · Page 1 of 1 (latest)

devout edge
#

function replaceKeysWithEnglishNames(obj: ContactInfo) {
    const newObj = {} as ContactInfo;
    for (const key in obj) {
      const index = labelNames.indexOf(key);
      console.log(index, key);
      newObj[englishNames[index]] = obj[key] === undefined ? "" : obj[key]; // error is here 
    }
    return newObj;
  }

const labelNames: string[] = [
    'Razón social de la compañía',
    'RFC',
    'Nombre público de la compañía (alias)',
    'Nombre del contacto',
    'Apellido paterno del contacto',
    'Apellido materno del contacto',
    'Sitio web',
    'Calle de la compañía',
    'Colonia',
    'Municipio',
    'Estado',
    'País',
    'Código postal',
    'Correo electrónico',
    'ExtNum',
    'teléfono'
  ];

 

  const englishNames: string[] = [
    'companyName',
    'rfc',
    'publicName',
    'contactName',
    'contactLastName',
    'contactSecondLastName',
    'website',
    'street',
    'neighborhood',
    'municipality',
    'state',
    'country',
    'zipCode',
    'email',
    'externalNumber',
    'phone'
  ];


/* Element implicitly has an 'any' type because expression of type 'string' can't be used to index type 'ContactInfo'.
  No index signature with a parameter of type 'string' was found on type 'ContactInfo'. */

I'm kind of new with typescript, i think it is due to me going through the arrays due to the ContactInfo interface. how can I solve this?

#
export interface ContactInfo {
    "Apellido materno del contacto"?: string | undefined;
    "Apellido paterno del contacto"?: string | undefined;
    "Calle de la compañía"?: string | undefined;
    "Colonia"?: string | undefined;
    "Correo electrónico"?: string | undefined;
    "Código postal"?: string | undefined;
    "Estado"?: string | undefined;
    "ExtNum"?: string | undefined;
    "Municipio"?: string | undefined;
    "Nombre del contacto": string | undefined;
    "Nombre público de la compañía (alias)": string | undefined;
    "País"?: string | undefined;
    "RFC": string | undefined;
    "Razón social de la compañía": string | undefined;
    "Sitio web"?: string | undefined;
    "teléfono"?: string | undefined;
    "contactId"?: number;
  }

  export interface BackEndRes {
    data: ContactInfo;
    status: number;
  }
true steppe
#

!:unsafe-keys

willow coveBOT
#
retsam19#0
`!retsam19:unsafe-keys`:

Since TS allows objects to have extra properties not specified in the type, it doesn't assume that all the keys on the type are the only keys on the object. This means that Object.keys returns string[] not a specific type, and for(const key in obj), key is string, (not keyof typeof obj).

If you wish to assume otherwise, this utility is often helpful:

// A signature for `Object.keys` that assumes the only keys are the ones indicated by the type
const unsafeKeys = Object.keys as <T>(obj: T) => Array<keyof T>;
true steppe
#

key is string there since ts can't guarantee they're all from ContactInfo

#

also englishNames[index] would be an arbitrary string as you've defined it, newObj is ContactInfo which doesn't actually have any of those strings

devout edge
#

so, if i create a new interface aka :


export interface CompanyInfo {
    companyName?: string | undefined;
    contactId?: number | undefined;
    contactLastName?: string | undefined;
    contactName?: string | undefined;
    contactSecondLastName?: string | undefined;
    country?: string | undefined;
    email?: string | undefined;
    externalNumber?: string | undefined;
    municipality?: string | undefined;
    neighborhood?: string | undefined;
    phone?: string | undefined;
    publicName?: string | undefined;
    rfc?: string | undefined;
    state?: string | undefined;
    street?: string | undefined;
    website?: string | undefined;
    zipCode?: string | undefined;
  }

it should work? i am still getting the indexing error tho

true steppe
#

there's like 3 issues there

#

this would only solve 1 and it looks like it introduces another

#

labelNames/englishNames would need to be typed more strictly

devout edge
#

ok, can you help me understand please? what would be a good starting point?

#

okay

true steppe
true steppe
devout edge
#

so, replace it with a hashmap?