Detecting if a variable in Typescript is an object defined by an interface with nested properties: Is there a method for accomplishing this?

Consider the following scenario:

interface EXAMPLE_OBJECT {
    "example1" : EXAMPLE_TYPE;
    "example2" : EXAMPLE_INTERFACE
}

type EXAMPLE_TYPE = string|number;

interface EXAMPLE_INTERFACE {
    "example3" : boolean;
}

How can we determine if a variable is an EXAMPLE_OBJECT?

Answer №1

Should you be seeking TypeScript to automatically generate runtime type guards, that functionality is not available. Nonetheless, the compiler does a commendable job of narrowing types based on your knowledge of the object being examined. Take, for example, a scenario where you are certain that something is either a TEST_OBJECT or a string:

function hasKey<K extends string>(k: K, x: any): x is Record<K, {}> {
  return k in x;
}

declare const obj: TEST_OBJECT | string;

if (hasKey("test2", obj)) {
  // it knows that obj is a TEST_OBJECT now
  console.log(obj.test1);
  console.log(obj.test2.test3 === false); 
} else {
  // it knows that obj is a string
  console.log(obj.charAt(0));
}

If you lack insight into the nature of the object under examination, @JoshCrozier suggests utilizing User-Defined Type Guards. By constructing these guards similar to how interfaces and types are formed, you can achieve clarity:

function hasKey<K extends string>(k: K, x: any): x is Record<K, {}> {
  return k in x;
}

function isTEST_INTERFACE(x: any): x is TEST_INTERFACE {
  return hasKey("test3",x) && (typeof x.test3 === 'boolean');
}

function isTEST_TYPE(x: any): x is TEST_TYPE {
  return (typeof x === 'string') || (typeof x === 'number');
}

function isTEST_OBJECT(x: any): x is TEST_OBJECT {
  return hasKey("test1", x) && isTEST_TYPE(x.test1) &&
    hasKey("test2", x) && isTEST_INTERFACE(x.test2);
}

// implementation:
declare const obj: TEST_OBJECT | string
if (isTEST_OBJECT(obj)) {
  console.log(obj.test1);
  console.log(obj.test2.test3 === false); 
} else {
  console.log(obj.charAt(0));
}

Trust this information proves useful.

Similar questions

If you have not found the answer to your question or you are interested in this topic, then look at other similar questions below or use the search

Notification within the conditional statement in React JS

I am working on validating phone number input within a React JS component using an if/else statement. If the user enters letters instead of numbers, I want to display a message saying "please check phone number". While I have been able to create a function ...

Error in TypeScript while running the command "tsd install jquery" - the identifier "document" could not be found

Currently, I am facing an issue with importing jQuery into my TypeScript project. In order to achieve this, I executed the command tsd install jquery --save, which generated a jquery.d.ts file and added /// <reference path="jquery/jquery.d.ts" /> to ...

Display responsive input field based on selected option in ionic2 dropdown menu

When the user selects 'Other' from the dropdown menu using Ionic2 and Angular2, I want to provide them with an option to enter their profession. Here is a visual representation of the select box: https://i.sstatic.net/CRjAl.png Below is the co ...

I am looking to transfer the value of one textbox to another textbox within a dynamic creation of textboxes using JavaScript

var room = 1; function add_fields() { room=$('#row_count').val()-1; room++; var objTo = document.getElementById('education_fields'); var divtest = document.createElement("div"); divtest.setAttribute("class", "form- ...

Conceal the div element five seconds after the registration process is completed

Is it possible to automatically hide a div 5 seconds after a user registers? Using the timestamp in PHP for the user's registration, there may be a way to achieve this with jQuery, but it's not certain. I found a script online that successfully ...

Retrieving the updated list after a child has been deleted from the Firebase Database

According to the documentation, the DataSnapshot received in the child_removed callback contains the old data for the removed child. I have a scenario where I am adding data using push and then trying to access the next value after the top child is remove ...

showing input using an array

I need some assistance with my JavaScript code. I have created three input boxes where users can add data, and then click a button to add the data into an array. The goal is to allow multiple users to input data and then display all values in the array alo ...

Currently in the process of modernizing an outdated method to a more up-to-date version in Jasmine, encountering issues related to

Currently working to update the method throwOnExpectationFailure to the newer one oneFailurePerSpec. According to the Jasmine documentation, this can be achieved by: Use the `oneFailurePerSpec` option with Env#configure After conducting research, I came ...

"Missing the import of material-ui search icons is causing a functionality issue

import React from 'react' import {Search} from "@material-ui/icons/Search" const App = () => { return ( <div> <Search/> </div> ) } export default App The exported component 'Search' (impor ...

Testing an Angular factory that relies on dependencies using JasmineJS

I have a factory setup like this: angular.module("myServices") .factory("$service1", ["$rootScope", "$service2", function($rootScope, $service2){...})]; Now I'm attempting to test it, but simply injecting $service1 is resulting in an &ap ...

Just diving into JavaScript, what makes jQuery so powerful?

As a newcomer to javascript (although functional programming is no problem for me), I find myself questioning some of the design choices made by jQuery. Is it too late to make changes now, or are they simply too ingrained in the framework? For example, the ...

Vue.JS component containing DOM elements outside of the designated $el scope

Transitioning from a custom front-end framework to Vue is a new adventure for me. Our website is gradually integrating Vue, and as we refactor old components, I've encountered an issue. My question is: Can a component create DOM elements outside of i ...

How can we include identical item names within a single JavaScript object?

My attempt at achieving the desired result involves creating an object like this: var obj = {id: id, items: "asdf", items: "sdff", test: varTest}; However, I face a challenge where I need to dynamically add two elements with the same name 'items&apo ...

Guide on incorporating one element into another with jquery

I am facing a challenge with the following code snippet: <p>Nuno</p> <p>Eimes</p> My goal is to transform it into this format: <p><a href="name/Nuno">Nuno</a></p> <p><a href="name/Eimes">Eimes& ...

A guide on displaying data from objects containing arrays in React using TypeScript

Hey there! I'm currently facing a challenge in rendering values within an object containing arrays. Let me show you an example of the object structure: data { info1: [{note: "this is note 1", status: true}], info2: [{note: "this i ...

Are the commands overlapping?

Currently, I am in the process of developing a dynamic discord chat bot using JavaScript and node.js. One of my goals is to implement a specific command without interfering with an existing one. The bot functions flawlessly across all servers where it is ...

Is it possible for Response.Redirect and OnBeforeUnload to cooperate effectively?

Is there a way to detect if the server-side code has sent a Response.Redirect in an OnBeforeUnload event? I need to alert the user before they navigate away from a page, but I don't want the prompt to appear when the server redirects. I'm dealin ...

The worth of the scope is evident, yet it remains undefined when trying to access it

Currently, I am in the process of developing an AngularJS directive. However, I have encountered an issue where a scope variable appears to be undefined when attempting to access it. Interestingly, upon printing out the scope, it is evident that the variab ...

Application fails to launch after disabling unsafe-eval in the restricted Content Security Policy settings

Description My application is facing issues due to having a restricted CSP policy that does not allow unsafe-eval for scripts. When I add a Content-Security-Policy header without unsafe-eval, my application fails to load. Minimal Reproduction The restric ...

The React function was misusing the useEffect hook, causing it to be

I seem to be encountering a problem when trying to call useEffect within this function. As someone who is relatively new to React, I may have made some noticeable mistakes, but dealing with this issue is becoming quite time-consuming. The function in ques ...