Finding the IP address of the client within the same network

After extensive research and Google searches, I have successfully obtained the local client IP address using JQuery in my Angular 6 project. However, upon building the application, I encountered errors that I believe are due to the JQuery code (specifically window.something) integrated within Angular.

Does anyone know how to achieve this solely with Angular, without relying on JQuery or third-party URLs like and other similar websites?

Code:

    ngOnInit() {
        var self = this;
        var localIp1 = ""; 
        $(document).ready(function(){
            window.RTCPeerConnection = window.RTCPeerConnection || window.mozRTCPeerConnection || window.webkitRTCPeerConnection;  
            var pc = new RTCPeerConnection({iceServers:[]}), 
            noop = function(){}; 

            pc.createDataChannel("");
            pc.createOffer(pc.setLocalDescription.bind(pc), noop);   
            pc.onicecandidate = function(ice){
                if(!ice || !ice.candidate || !ice.candidate.candidate)  return;

                var localIp = /([0-9]{1,3}(\.[0-9]{1,3}){3}|[a-f0-9]{1,4}(:[a-f0-9]{1,4}){7})/.exec(ice.candidate.candidate)[1];
               // this.localIpAddress = myIP;
                localIp = localIp.replace(/\./g, '-');
                sessionStorage.setItem("LOCAL_IP", localIp);
                $.ajax({ 
                    type: "GET",
                    dataType: "json",
                    url: "http://localhost:8080/api/setLocalIpAddress/" + localIp,
                    success: function(data){        
                      console.log(data);
                    }
                 });
            };
        });
        this.localIp = sessionStorage.getItem("LOCAL_IP");
}

Error:

ERROR in src/app/selectline/select-line.component.ts(35,20): error TS2339: Property 'RTCPeerConnection' does not exist on type 'Window'.
src/app/selectline/select-line.component.ts(35,47): error TS2339: Property 'RTCPeerConnection' does not exist on type 'Window'.
src/app/selectline/select-line.component.ts(35,75): error TS2339: Property 'mozRTCPeerConnection' does not exist on type 'Window'.
src/app/selectline/select-line.component.ts(35,106): error TS2339: Property 'webkitRTCPeerConnection' does not exist on type 'Window'.
src/app/selectline/select-line.component.ts(39,16): error TS2339: Property 'createDataChannel' does not exist on type 'RTCPeerConnection'.

Thanks a lot in advance for any help!

Answer №1

I successfully adjusted the code provided and created a sample StackBlitz without relying on jQuery or external libraries. To view the running code, you can visit this example StackBlitz.

As explained in my previous comment, incorporating module augmentation from the TypeScript handbook is essential for this task. In order to enhance the window object to acknowledge the global properties being accessed, I included the following code snippet:

declare global {
  interface Window {
    RTCPeerConnection: RTCPeerConnection;
    mozRTCPeerConnection: RTCPeerConnection;
    webkitRTCPeerConnection: RTCPeerConnection;
  }
}

The current specification for RTCPeerConnection seems to have changed compared to the original code reference. Adapting it to align with the updated spec led me to revise the code as follows:

import { Component, NgZone } from '@angular/core';

// Module Augmentation
declare global {
  interface Window {
    RTCPeerConnection: RTCPeerConnection;
    mozRTCPeerConnection: RTCPeerConnection;
    webkitRTCPeerConnection: RTCPeerConnection;
  }
}

@Component({
  selector: 'my-app',
  templateUrl: './app.component.html',
  styleUrls: [ './app.component.css' ]
})
export class AppComponent  {
  name = 'Angular';
  localIp = sessionStorage.getItem('LOCAL_IP');
  
  // Regular Expression for IP Address
  private ipRegex = new RegExp(/([0-9]{1,3}(\.[0-9]{1,3}){3}|[a-f0-9]{1,4}(:[a-f0-9]{1,4}){7}/);

  constructor(private zone: NgZone) {
  }

  ngOnInit() {
    this.determineLocalIp();
  }
  
  private determineLocalIp() {
    window.RTCPeerConnection = this.getRTCPeerConnection();

    const pc = new RTCPeerConnection({ iceServers: [] });
    pc.createDataChannel('');
    pc.createOffer().then(pc.setLocalDescription.bind(pc));

    pc.onicecandidate = (ice) => {
      this.zone.run(() => {
        if (!ice || !ice.candidate || !ice.candidate.candidate) {
          return;
        }

        this.localIp = this.ipRegex.exec(ice.candidate.candidate)[1];
        sessionStorage.setItem('LOCAL_IP', this.localIp);
        
        pc.onicecandidate = () => {};
        pc.close();
      });
    };
  }

  private getRTCPeerConnection() {
    return window.RTCPeerConnection ||
      window.mozRTCPeerConnection ||
      window.webkitRTCPeerConnection;
  }
}

It's important to note that the logic inside the onicecandidate method will operate outside the Angular zone, meaning any changes to component properties will not trigger UI updates within Angular. To ensure Angular recognizes these changes, it's necessary to obtain an Angular zone reference and execute the code within it using this.zone.run(() => { ... });. For further details on zones in Angular, you may find this blog post about zones in Angular informative.

Answer №2

The link provided in the previous answer, https://stackblitz.com/edit/angular-get-local-ip, did not function correctly for me.

After encountering issues with the code sample, I made some modifications:

pc.createDataChannel(''); 

I altered this line to read:

pc.createDataChannel("rtc");

Additionally, I updated the following line regarding ice servers:

[{ urls: "stun:stun.l.google.com:19302" }]

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

Adjusting the transparency level of the JavaScript thumbnail

I have implemented a plugin to showcase an image carousel on my website. The navigation thumbnails in the carousel are currently set to appear "greyed out" when not selected. Is there a way to adjust the level of grey for these thumbnails? Check out the l ...

Angular reactive form encountered an issue with an incorrect date being passed

Currently, I am utilizing the PrimeNg calendar module to select a date. Here is the code snippet: <p-calendar formControlName="valid_till" [dateFormat]="'mm/dd/yy'"></p-calendar> Upon selecting a date like 31st J ...

The jQuery Input Box Autocomplete Feature

After creating an autocomplete box using jQuery and PHP to fetch data from the database, I encountered a slight issue. Everything works fine except that when I start typing in the input box, it retrieves all results instead of only those similar to what I ...

Encapsulation in Angular Material: mat-error

Considering encapsulating the mat-error within its own component due to the lengthy text. The proposed solution is: <form [formGroup]="form"> <mat-form-field> <input matInput formControlName="title" placeholde ...

Is there a way to incorporate my getter into a computed property?

My Vuex Store is built using Vuex module decorators and I am facing an issue with using a getter for a computed property. Here is my code: @Module export default class WorkoutModule extends VuexModule { _workout: Workout; @Mutation startWork ...

Guide to organizing the table according to the values (timestamps) in a specific column

In one of the tables I'm working with, there is a column called uploadedOn. You can see it in action here: https://stackblitz.com/edit/angular-ivy-tntvst?devToolsHeight=33&file=src/app/app.component.ts 1: https://i.stack.imgur.com/aQ6wh.png. My g ...

Tips on Extracting Data from an ID

Is there a way to retrieve the ID of a radio button when it is clicked? <script> $(document).ready(function() { $('label').click(function() { var total = 0; $('.option ...

Stop the automatic display of the dropdown menu

How can I prevent the dropdown menu from automatically showing when I remove the 'hidden' class in jQuery: Sample HTML: <div class="btn-group btn-group-xs friend-request tooltiped" data-toggle="tooltip" title="Add as friend"> <button ...

When running the npm install command for Angular, an error occurred stating: "npm ERR! Maximum call stack

Upon running npm install, I encountered the following message: npm WARN deprecated <a href="/cdn-cgi/l/email-protection" class="__cf_email__" data-cfemail="2256510f514b4f524e470f4351566213100c160c12">[email protected]</a>: NOTICE: ts-si ...

Make sure to review the data table once more by clicking on the submit button

After pressing the update/submit button, I would like my dataTable to refresh and retrieve the data from the database again. I attempted the following: $('#ManageForms').dataTable().dataSource.read(); While this solution seemed to work with ke ...

I am looking to modify a particular value within an array of objects, but for some reason, the update is not being applied correctly

When attempting to copy the array, I update the selected value of a specific object based on the matching memberId. This process works well for a single member, however, issues arise when there are multiple members as the updating doesn't work correct ...

Tips for hiding a bootstrap modal in Angular4 when it has no content

I am currently working on an Angular 4 e-commerce application. One of the requirements is to hide a bootstrap modal when there are no products in the cart. When a user selects some products, they are added to the mycart modal screen. The user also has the ...

Combining JSON strings to simplify AJAX requests

I am currently working on a project that involves processing Web SQL rows. The current code sends a request to the server for every row, but I want to merge all the rows together into a multidimensional JSON object. However, I have been unable to find any ...

Invoke a PHP function once the jQuery timer counts down to zero

In this scenario, imagine the user has a limited 45 minutes to login. How can we trigger a PHP function to log out once the Jquery timer hits 0? Below is the code snippet: <script type="text/javascript"> function startTimer(duration, display) { v ...

Examining the potential of a promise within a dynamic import feature in Angular

Here's a code snippet that I'm working with: The component file (component.ts) looks like this: async ngOnInit() { import('dom-to-image').then(module => { const domToImage = module.default; const node = document.getEl ...

Load a URL using JQuery and place the content into the specified target element within the current

While working on a project, I encountered an issue with loading external content from a URL using jQuery's .load() function. This functionality was triggered by an onclick event and the parent document was a prompt window. The following is the HTML c ...

Hold off until the observable has finished

map((tasks): any => { return tasks.map(task => ({ ...task, status: this.getStatus(task.owner, task.delegationState, task.assignee, task.id), })); }); I utilize the getStatus method within the map() operator from rxjs. getStatus( ow ...

Creating interactive dropdown menus with PHP and Catalyst using Jquery

Currently, I am working on incorporating cascading dropdown menus into a catalyst web app. The main goal is to allow users to select a database table from the first dropdown menu and have the columns of that table populate the second dropdown menu. To achi ...

PHP not receiving data from jQuery Ajax (POST) request

Below is an Ajax function that sends data from a page to the same page for interpretation by PHP. When using Firebug, it is observed that the data is being sent, but not received by the PHP page. However, if we switch to a $.get function and retrieve the ...

implementing a new class for event handling that includes the toggleClass function

I'm not a full-time jQuery or JavaScript developer, so please forgive me if this is a silly question. I believe I require something similar to the live function for swapping classes in order to handle the values associated with a selector. This is th ...