Obtain the object literal string with additional decorative strings surrounding it

In my current Typescript code, I have an object literal structured like this:

const MyNamesStrings = {
    a: {
        b: "hello",
        c: "bye"
    }
    d: {
        e: "qwerty"
    }
}

However, I am looking for a way to wrap these strings with additional characters every time they are accessed. Writing the same wrapper characters within the literal seems messy and repetitive. I believe encapsulating this functionality in a class called MyNames would make it easier to manage.

The desired outcome is to have a MyNames class that acts as a proxy with features such as:

const ab = MyNames.a.b //"[${hello}]" where the extra characters surround the text.
const ac = MyNames.a.c //"[${bye}]"

Is it possible to achieve this using Javascript/Typescript? If not, alternative approaches can be explored to solve this issue.

Answer №1

If you find yourself in need of the specific functionality you are describing, one option is to utilize a true Proxy, provided that your JavaScript engine supports ECMAScript 2015 or newer. While this approach may be considered excessive for your particular situation, if MyNamesStrings remains unchanged, converting it to MyNames just once would be more efficient. However, for the sake of discussion, let's assume the use of a proxy is necessary. Below is one potential implementation:

function makeStringWrappingProxy<T extends object>(t: T): T {
  return new Proxy(t, {
    get<K extends keyof T>(target: T, prop: K) {
      const val = target[prop];
      if (typeof val === 'string') {
        return '[${' + val + '}]';
      } else if (typeof val === 'object') {
        return makeStringWrappingProxy(val as T[K] & object);
      } else {
        return val;
      }
    }
  });
}

The concept involves creating a proxy that intercepts all attempts to access properties within the object. When retrieving a string property, it will return the wrapped string instead. In the case of an object property, it will return a proxy for that property (allowing for nested property wrapping). Otherwise, it simply returns the property itself.

Let's observe this in action:

const MyNames = makeStringWrappingProxy(MyNamesStrings);
const ab = MyNames.a.b //"[${hello}]" expected output
const ac = MyNames.a.c //"[${bye}]" also expected result.

As demonstrated, the solution works as intended! It is important to note that utilizing proxies comes with trade-offs - they may not offer optimal performance (each property access triggers function calls), compatibility issues with older versions of ECMAScript, and can lead to unexpected behaviors (modifying a property may not reflect the change when accessed later). The decision ultimately lies with your specific requirements.

I hope this explanation proves helpful. Best of luck!

Answer №2

Essentially, you have the option of creating a custom getter function that allows you to access properties in a different way. Instead of directly accessing MyNamesStrings.a.b, you can now use MyNamesStrings.propGetter('a.b')

var MyNamesStrings = {
  a: {
    b: "hello",
    c: "bye"
  },
  d: {
    e: "qwerty"
  },
  propGetter: function(loc, start = "[${", end = "}]") {
    var split = loc.split('.');
    var value = this;
    for (var i = 0; i < split.length; i++) {
      if (value) {
        value = value[split[i]];
      }else{
          //stop looping because the previous value doesn't exist.
          break;
      }
    }
    return value ? start + value + end : undefined;
  }
}

var result = MyNamesStrings.propGetter('a.b');
var result2 = MyNamesStrings.propGetter('d.e');
var result3 = MyNamesStrings.propGetter('f.g.h.i');

console.log(result);
console.log(result2);
console.log(result3);

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

Change the classes of the body prior to the initial rendering

I know this may seem like a difficult task, and I understand that what I want to achieve might be nearly impossible. My goal is to incorporate a dark/light mode switch on my website. The challenge lies in the fact that the site consists of static files on ...

Currently I am developing a Minimax Algorithm implementation for my reversi game using react.js, however I am encountering a RangeError

I've been implementing a Minimax Algorithm for my reversi game to create a strong AI opponent for players. However, I ran into the following error message: "RangeError: Maximum call stack size exceeded" How can I go about resolving this issue? Here ...

Matching with Regex beyond the limits

Trying to extract a body tag using regex and then replace it with an appended string. However, encountering an issue where the regex is selecting more content than intended. regex: /<body.*[^>]>/i test string: <bla bla ><body class=&apo ...

Automatically populating username and password fields

Is it possible to set up automatic username and password filling on my website for users who have saved their login information in their browser? I want the user to just hit enter to login. Some websites already have this feature enabled, but others requi ...

Guide to setting a dynamic value for an input List property in Angular

How can I render multiple dropdowns in Angular based on the response from an API? Currently, when I retrieve data from the API, I am seeing the same information displayed in both dropdown controls. Is there a way to assign dynamic values to the "list" prop ...

Received undefined instead of a Promise or value from the function in Nodemailer

I'm currently exploring cloud functions and trying to implement email notifications for document creation triggers in Firestore. I found a helpful tutorial that guided me through the process, but I encountered an error while analyzing the cloud functi ...

Unable to assign a value to a null property during the onchange event

I'm currently working on a project where I need to display flight details based on the selected flight number. To achieve this, I have created a dropdown menu that lists all available flight numbers and a table displaying various flight details such a ...

What is the process of connecting a Yarn module to a Docker container in another repository?

I'm currently facing a challenge in linking a module to a Docker container from another repository. To provide some background, I have a container hosting a React application named launch-control-admin. This project relies on a yarn module called @com ...

Using vanilla JavaScript with AJAX, the second asynchronous post will only be sent once the first post has been successfully sent

I am in the process of creating a HotSpot that offers internet access once users input their email addresses. To make this function properly, I need to execute two separate AJAX posts: The first one sends hidden username and password details to the rout ...

JavaScript's failure to properly handle UTF-8 encoding

Here is a snippet of code that I found on Stack Overflow and modified: <?php header('Content-Type: text/html; charset=ISO-8859-1'); $origadd = $_SESSION["OriginAdd"] // $_SESSION["OriginAdd"] contains the value "rueFrédéricMistral"; echo $o ...

Tips for achieving proper styling and formatting of elements in jQuery UI

I've encountered an issue when trying to use jQuery UI after downloading it multiple times. In the examples provided with the download, the UI elements appear perfectly formatted, but when I implement them on my own pages, the styles and formatting ge ...

Troubleshooting: ReactJS CSS Class Issue

I'm fairly new to working with ReactJS and I've encountered an issue while trying to create a class for a specific form. Below is the code I've written: import React, { Component, PropTypes } from 'react'; import s from './s ...

Internet Explorer 9 does not display content until the ajax/json function has finished executing

I have encountered an issue with my code regarding updating a div element. The first innerHTML call seems to be ineffective and does not render in the browser. However, the second innerHTML call works as expected by appending "Complete" once the ajax call ...

The checkbox event listener becomes dysfunctional when the innerHTML of its container is modified

My current challenge involves creating checkboxes with a blank line inserted after each one. I also need these checkboxes to trigger a function when changed. This is my code snippet: var div = document.getElementById("test"); var cb1 = document.createEl ...

Tips for refreshing the appearance of a window in angular when it is resized

I have a chat feature integrated into my application. I am looking to dynamically resize an image within the chat window when the width of the window falls below a certain threshold. Is there a method available to modify the CSS style or class based on the ...

What are the drawbacks of removing comments from polyfills.ts in Angular CLI when using Internet Explorer?

Encountering a similar problem as described in Angular4 Application running issues in IE11. Although the suggested solution resolved the issue, I am left wondering why the lines referring to necessary polyfills for IE9, IE10, and IE11 were initially comm ...

typescript: declaring types in a separate JavaScript file

Imagine you have a JavaScript library that exports some types for use (let's call it js1.js). You also have some TypeScript code sitting in a <script type="module"> tag that you want to use these types with (let's say ts1.ts). To make this ...

Tips for wrapping text to fit the width of a column

Hello, I have a table with varying column widths as shown below ${"#goldBarList"} table tr td:first-child{width:5%;} ${"#goldBarList"} table tr td:first-child+td{width:5%;} ${"#goldBarList"} table tr td:first-child+td+td{width:6%;} ${"#goldBarList"} table ...

Can you display names in capital letters from the randomUser.me API?

Apologies if this is not the appropriate platform for my query. Just to provide context, I am a designer with minimal experience in APIs and Javascript. I am currently utilizing the randomUser API to create a JSON file or URL that can be integrated into I ...

A guide on utilizing Stripe's payment_intent_data feature to automatically send an email to the customer following a successful transaction

I am struggling to send an email to the client after a successful payment. The documentation mentions setting "payment_intent_data.receipt_email", but my code below is not working as expected (no emails are being received). How should I properly configur ...