Checking at compile time whether a TypeScript interface contains one or multiple properties

Is there a way to determine if a typescript interface contains at least one property at compile time without knowing the property names?

For example, with the interfaces Cat and Dog defined as follows:

export type Cat = {};
export type Dog = { barking: boolean };

I require a conditional type HasAnyProperties<T> to provide the following results:

type catHasProperties = HasAnyProperties<Cat>;   // false   
type dogHasProperties = HasAnyProperties<Dog>;   // true    

I specifically do not want to:

  • Use Object.keys(obj).length
  • Enforce or require known properties. I only want to check.

This might seem like an unusual request, but I am actually trying to filter a type and then determine if anything remains. This information is then used to potentially add a new property on a mapped type.

Various attempts have failed so far:

// This always returns true
type HasAnyProperties<T> = T extends { [key: string]: any } ? true : false;

If possible, the solution may resemble something like RequireAtLeastOne.

Answer №1

It's actually quite straightforward:

 export type HasSomeAttributes<T> = {} extends T ? false : true;

This solution worked perfectly for me. If anyone encounters any challenges with this approach or has a better one, feel free to share your thoughts in the comments or post a new response.

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

Using Threejs to create an elbow shape with specified beginning and ending radii

I'm a beginner in Threejs and I'm attempting to create an elbow shape along a curved path with varying begin_radius and end_radius, using the curve_radius and an angle. However, I haven't been successful in achieving the desired results. C ...

Exporting a constant as a default in TypeScript

We are currently developing a TypeScript library that will be published to our private NPM environment. The goal is for this library to be usable in TS, ES6, or ES5 projects. Let's call the npm package foo. The main file of the library serves as an e ...

Debug errors occur when binding to computed getters in Angular 2

Currently, I am integrating Angular 2 with lodash in my project. Within my model, I have Relations and a specific getter implemented as follows: get relationsPerType() { return _(this.Relations) .groupBy(p => p.Type) .toPairs() ...

How can I populate a mat-table in Angular 7 with data stored in an object?

At the moment, my code is set up to populate a table with data. In my component.ts file: import { HttpClient } from "@angular/common/http"; import { Component, OnInit } from "@angular/core"; import { FormBuilder, FormGroup, Validators } from "@angular/fo ...

Guide to displaying loading progress during server response delay in React with TypeScript

I need to find a way to update the loading state to false once the server responds. The challenge is that the response occurs in one component, while the progress bar is located in another. To illustrate the scenario: const Form: React.FC = () => { ...

What steps are involved in constructing Jodit from scratch?

Seeking a non-minified, readable version of Jodit, I attempted to build it myself. However, my lack of experience with composer, node, npm, webpack, TypeScript, and other tools has left me struggling. Is there anyone who can guide me through the process s ...

Set up linter rules that utilize `useEffect` in place of `React.useEffect` (utilizing named export rather than full export)

It's important in our codebase to always use: import { useEffect } from 'react'; instead of: import React from 'react'; // use in code as `React.useEffect` Can we enforce this rule with longer eslint rules? If so, how can we impl ...

Calling a typed function with conditional types in Typescript from within another function

In my attempt to create a conditional-type function, I stumbled upon this question on Stack Overflow. Unfortunately, it seems that the approach doesn't work well with default values (regardless of where the default value is placed). Following the advi ...

Creating a feature that automatically determines the data type of a value using the provided key

My object type has keys that map to different types: type Value = { str: string; num: number; }; I am working on creating a universal format function: const format = <K extends keyof Value>(key: K, value: Value[K]): string => { if (key === ...

Issue: (SystemJS) Unable to find solutions for all parameters in $WebSocket: ([object Object], [object Object], ?)

Upon running the code snippet below, an error is thrown: Error: (SystemJS) Can't resolve all parameters for $WebSocket: ([object Object], [object Object], ?). app.component.ts import { Component } from '@angular/core'; import {$WebSocket} ...

Breaking down code with Webpack for future extensibility

We are in the process of developing a game and have successfully implemented code-splitting to separate vendor libraries and the core engine into individual bundles, as well as splitting levels into separate bundles. As we plan for future releases where t ...

Error: inability to execute performanceMeasurement.startMeasurement due to its absence in the function definition

An error occurred when attempting to login using @azure/msal-react in Next 13. Upon checking the error log, it was found that the error originated from the core library @azure/msal-react. Even after trying with a login popup, the error persisted. In my co ...

When I pass an array of objects to Firefox (using TypeScript) and retrieve the data, I find that I am unable to retrieve it in the form of an array of objects

When it comes to saving and retrieving data from a Firebase database, I seem to be encountering an issue where the type of data retrieved does not match what I am expecting. Let me break down what I am doing and the problem I am facing: Saving data To sa ...

Unable to utilize the web-assembly Rust implementation due to the error stating 'Cannot access '__wbindgen_throw' before initialization'

Looking to integrate some web-assembly into my project, I started off by testing if my webpack setup was functioning properly and able to utilize my .wasm modules. Here's a snippet of what I came up with: #[wasm_bindgen] pub fn return_char() -> cha ...

Translating from a higher-level programming language to a lower-level programming language

Is compilation effectively the transformation of high-level programming languages (HLL) into machine code or low-level language? If so, why is TypeScript (a HLL) compiled to JavaScript (also a HLL) instead of being compiled to a low-level language? ...

Identifying the End of an HTML Video in Angular 2

Seeking assistance with detecting the end of an HTML video in Ionic2 (Angular2 and Typescript). The relevant code snippets can be found below: Template: <video poster="" id="v" playsinline autoplay webkit-playsinline onended="vidEnded()"> <s ...

Verify the legitimacy of the object

I'm encountering an issue while attempting to create a function that verifies the validity of an object. const isPeriodValid = (period: Period | null): boolean => { return period && period.start && period.end; } export interfac ...

Develop a new entity utilizing Array in Javascript

let DaysArray: any = ["monday", "tuesday", "wednesday", "thursday", "friday", "saturday", "sunday"] I am looking to transform the above array into an Object structure as shown below: let DaysObject: any = { time: { headerName: "" }, m ...

Troubleshooting problem with Angular Click Outside Directive and unexpected extra click event issue

The challenge I'm facing involves implementing a custom Click Outside Directive for closing modal dialogs, notifications, popovers, and other 'popups' triggered by various actions. One specific issue is that when using the directive with pop ...

Snapshots testing app Expo TypeScript Tabs App.tsx

After setting up an Expo project with Typescript and Tabs, I decided to add unit testing using Jest but ran into some issues. If you want to create a similar setup, check out the instructions here: . Make sure to choose the Typescript with Tabs option whe ...