Using Angular 4's ngModel can result in the transformation of data type from 'number' to 'string'

I am facing an issue with my Angular4 app where data captured from a form is stored in DynamoDB. The problem arises when an input field typed as 'text' is bound to a Typescript 'number' field, which seems to be converting the object value to a 'string'. Changing the HTML Input type to 'number' is not an ideal solution due to the unwanted increment/decrement decorators on the form field. I am exploring alternative methods to maintain the desired data structure while dealing with this issue.

The structure in my sample.component.ts file is as follows:

export class Course {
  Id: number;
  Name: string;
}
...
courseInstance: Course;

saveCourse() {
    JSON.stringify(this.courseInstance);
}

The code in my sample.component.html file is as follows:

<div>
  <label for="courseid">Course ID: </label>
  <input type="text" class="form-control"[(ngModel)]="courseInstance.Id" name="courseid">
</div>
<div>
  <label for="courseName">Course Name: </label>
  <input type="text"  class="form-control"[(ngModel)]="courseInstance.Name" name="courseName">
</div>
<div>
  <button type="button" class="btn btn-info btn-lg" (click)="saveCourse()">Save</button>
</div>

When using JSON.stringify(this.courseInstance), the output results in something similar to

{"Id":"100","Name":"Test course"}

Where the value 100 is represented as a string. However, when directly creating an instance without using the form, the output of JSON.stringify(courseInstance); is

{"Id":100,"Name":"Test course"}

Attempting to store the object in DynamoDB using PutItem, the Id value fails type check when the data comes from an HTML form.

It is perplexing that Typescript typing does not take precedence over the HTML 'text' input type. I am still exploring possible solutions to address this issue.

Answer №1

Transform the data type from text to number in order to restrict input to numbers only.

<input type="number" class="form-control"[(ngModel)]="courseInstance.Id" name="courseid">

Answer №2

Utilizing the [(ngModel)] syntax is limited to setting a data-bound property. If your requirements call for more flexibility or a different approach, consider using the expanded form provided below.

 <div>
  <label for="courseid">Course ID: </label>
  <input type="text" #ref class="form-control" [ngModel]="courseInstance.Id" (ngModelChange)="onDataChange(ref.value)" name="courseid">
</div>

The ngModel data property assigns a value to the element's property, while the ngModelChange event property detects changes in the element's value. To achieve the desired outcome, consider using parseInt. Utilize ngModelChange to handle keystroke events, and for value debouncing, implement a Subject with the debounceTime() operator. A Subject can function as both an observer and an observable.

Within your component:


import { Subject } from 'rxjs/Subject';
import { debounceTime } from 'rxjs/operators;

debouncer = new Subject();

constructor() {
  this.debouncer
    .debounceTime(1000)
    .subscribe((val) => {
      console.log(val);
      this.courseInstance.id = parseInt(val, 10);
    });
}

onDataChange(value) {
  this.debouncer.next(value);
}

Answer №3

Angular does not currently offer type checking for property binding and event binding. There is an ongoing issue on their github platform addressing this concern: https://github.com/angular/angular/issues/16952

To address this issue, I recommend updating your input to type number and applying the following CSS in your component:

input[type=number]::-webkit-inner-spin-button, 
input[type=number]::-webkit-outer-spin-button { 
  -webkit-appearance: none; 
  margin: 0; 
}

Additionally, you can view a demonstration of this solution on Stackblitz: https://stackblitz.com/edit/angular4-ngmodel-changes-type-of-data-from-number-to-string

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

Effortlessly uploading large files using axios

I am currently facing an issue and I am seeking assistance. My goal is to implement file chunk upload using axios, where each chunk is sent to the server sequentially. However, the requests are not being sent in order as expected. Below is a snippet of m ...

Troubleshooting: Unable to delete data using $http in AngularJS

When using the $http service in Angular JS to call an API for deleting a message, I am receiving a successful response but the value is not actually being deleted. Interestingly, when I directly access the same API in my browser, the message gets deleted s ...

Using javascript, how can you fill in the missing dates within an array of objects?

I need to populate this object with dates starting from today up to the next 7 days. Here is my current object: let obj = { "sessions": [{ "id": 0, "available_capacity": 3, "date": "15-05- ...

Word.js alternative for document files

I'm on the lookout for a JavaScript library that can handle Word Documents (.doc and .docx) like pdf.js. Any recommendations? UPDATE: Just discovered an intriguing library called DOCX.js, but I'm in search of something with a bit more sophistic ...

extract elements from dataset

Attempting to splice an array but encountering index issues var kode_pelayanan = []; function deleteKodePelayanan(index){ kode_pelayanan.splice(index, 1); console.log(kode_pelayanan); } Experimented in the console with an array for kode_pelayanan ...

Iterate over a collection of HTML elements to assign a specific class to one element and a different class to the remaining elements

Forgive me if this is a silly question, but I have a function named selectFace(face); The idea is that when an item is clicked, it should add one class to that item and another class to all the other items. This is what I currently have: HTML <div c ...

Detect the size changes of a React DOM node using hooks

Is it possible to measure a React DOM node during the window resize event? I followed the example provided in the React hooks-faq, but it seems to only work for the initial render. When I tried adding a useEffect to listen for the resize event, the callb ...

What is the best way to ensure that the checkbox is not affected when you click on the area?

If the user interacts with the checkbox, I don't want the handleClick function to execute. Is there a way to exclude it or prevent the click event from triggering? <div ... onClick={this.handleClick}> <div> some content here < ...

How exactly did Google Fiber design their onboarding guide?

Are you using HTML5 canvas animation or Flash for this website? It's a bit difficult for me to discern. Thank you! ...

Meteor is constantly tuning in to receive updates from the MongoDB database

As I work on developing a game with Meteor, I have been advised by many to use mongo db due to its vanilla nature, speed, and reactivity. I have come to understand that I need to actively monitor updates in mongo db in order to react to received data and u ...

Using Function Call to Generate Components in React

Being tired of repeatedly defining states to render Components based on conditions, I often find myself just wanting to display notifications or alerts. My current dilemma is figuring out how to render a component by invoking a function from within that co ...

Updating the state of an object within a mapping function

I've been struggling with this issue for two days now. Despite my efforts to find a solution online, I am still stuck and starting to believe that I might be missing something. The main functionality of the app is to click a button and watch an apple ...

Passing variables through a promise chain and utilizing the finally method

My current endeavor involves constructing a log for an Express API, yet I am encountering difficulties in extracting the data for logging. I have successfully logged the initial req and res objects within the finally block, but I am uncertain about how to ...

When changing recipients in Firebase, the Javascript code fetches the same message multiple times even though there is only a single message stored in the database

In the process of developing a chat application using Firebase and JavaScript, I have come across an issue. Whenever I switch receivers multiple times, the message I send is fetched multiple times even though it is only sent once to the database. var selec ...

Automated Menu Selection using Selenium

I'm currently facing a challenge in writing a Python script using Selenium to interact with a webpage. I am struggling to use the .click() method to select an expandable list on the page. Despite successfully logging in and navigating to the desired p ...

What is the best way to implement a timer or interval system in React and Next.js that continues running even when the tab is not in focus or the browser is in

I am attempting to create a stopwatch feature using next js. However, I have encountered an unusual issue where the stopwatch does not function correctly when the tab is not focused or when the system goes to sleep or becomes inactive. It appears that the ...

Deactivate the button while the form is being submitted

I need a way to prevent users from clicking the submit button multiple times while the form is being processed by the server. Below is the solution I have come up with: clear() { this.count++ this.formGroup.get('name').reset(null); ...

Passing a JSON object as a parameter in a dynamically created element's click event using JavaScript/AngularJS

How to pass a JSON object as a parameter in the click event of a dynamically created element using JavaScript and AngularJS? var _dataObj = "{"sor_SourcingAgentId":1,"sor_Name":"xx"}" var _dynHtml= '<input type="button" ng-click="fnSelectcustom ...

What is the most effective way to retrieve the count of users who have logged in within the past three months by utilizing Jquery

I am seeking to retrieve the count of users who have logged in the last three months utilizing a JSON API and Jquery. This is my current progress: $.getJSON('users.json', function(data) { var numberOfUserLogged = 0; var d1 = ...

Transforming a sophisticated nested array containing named values into JSON format

I am facing a challenge with converting an array into JSON format. The array, named classProfiles, has the following structure (seen after inspecting console output): Buildings_clear: Array(0) band1: [Min: 24, Max: 24, Mean: 24, Median: 24, StdDev: 0] ...