Is it possible to access values stored in an AngularJS service without explicitly sending them back?

Any insights on how this system operates would be greatly valued. My service stores session-specific variables, like table sorting preferences, and other related data.

The code appears to be functioning correctly. However, my query pertains to retrieving these values without directly returning the variable. Do I need to implement a Getter function for this purpose? Are these variables somehow made public through the setter method, or is there an error in my approach? Could it be because of my utilization of this, or is it simply a lack of understanding concerning JavaScript scoping? :)

Here's the snippet of the Service code:

angular.module('myApp').service('sessionService', function () {

  this.searchView = 2; // <-- edited in, forgot this

  return {
    setSearchView: setSearchView
  };

  function setSearchView (searchView) {
    this.searchView = searchView;
  }

});

Then, we move on to the controller.

angular.module('myApp').controller('SearchCtrl', function (sessionService) {

  console.log(sessionService.searchView); //undefined

  sessionService.setSearchView(1);

  console.log(sessionService.searchView); // 1 

});

After modifying the searchView from the controller, it can then be effortlessly accessed as illustrated above.

I welcome any help in comprehending this matter.

EDIT: I neglected to mention that this.searchView was actually present initially, yet the same outcome prevails in the console.log within the controller.

Answer №1

Services are often referred to as 'singletons', indicating that you can set a variable that is not directly accessible or returned, and it will retain its value for the duration of the UI lifecycle. If you wish to access sessionService.searchView, there are a few ways to achieve this:

1) Define a private variable searchView and then include a getter function in your return statement:

  return {
    setSearchView: setSearchView,
    getSearchView: function() {
        return searchView;
    }
  };

2) Alternatively, create a private variable searchView and include it in your return statement:

var searchView;

return {
    setSearchView: setSearchView,
    searchView: searchView
};

Answer №2

When you add the service to the controller

angular.module('myApp').controller('SearchCtrl', function (sessionService) {

you receive an instance of the service definition function. Essentially, your sessionService is like

new function () {

  return {
    setSearchView: setSearchView
  };

  function setSearchView (searchView) {
    this.searchView = searchView;
  }

}

meaning that the function you provided when defining the service is invoked using new. The new keyword indicates it's being used as a constructor function.


Now, let's talk about new and Javascript constructors - if the constructor function returns an object, that object becomes the result of new. And this in the member methods refers to that object.

In essence, your service definition acts as a constructor function. In pure Javascript, it could resemble something like this.

function SessionService () {
  return {
    setSearchView: function (searchView) {
       this.searchView = searchView;
    }
  };
}

var sessionService = new SessionService();

Notice how SessionService is capitalized to denote a constructor, while sessionService follows camel case as an instance.


With this understanding, calling

sessionService.setSearchView(1);

sets the searchView property of the sessionService instance to 1. Similarly, accessing

sessionService.searchView

refers to the same property you set earlier.

You can also directly assign to sessionService.searchView with 1, as you're essentially operating on the sessionService instance.

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

Transform the razor model into JSON format and then integrate it with Angular

Currently, I am attempting to integrate AngularJs with MVC5. However, the challenge I am facing is extracting data from the razor @model using AngularJs. After several unsuccessful attempts at converting the @Model to JSON, I am still stuck. _Layout.csht ...

Exploring ways to incorporate various classes into my validate() elements using jQuery

I'm currently using the jQuery method validate to verify this particular form: <form id="emailRecover"> <div class="row light-field-container error-container"> <input type="text" id="dniPassword" name="dniPassword" requ ...

Having trouble updating an array in a mongoose document?

Need help with updating an array in a document by adding or replacing objects based on certain conditions? It seems like only the $set parameter is working for you. Here's a look at my mongoose schema: var cartSchema = mongoose.Schema({ mail: Stri ...

Remove the last column from the UI grid and add a Bootstrap dropdown menu inside each cell

In order to retrieve the data from the ui-grid, I implemented the following method: $scope.getData = function() { var a = $scope.gridOpts.data; alert(JSON.stringify(a)); } However, I noticed that it displays an extra column which I want to remove ...

The (window).keyup() function fails to trigger after launching a video within an iframe

Here is a code snippet that I am using: $(window).keyup(function(event) { console.log('hello'); }); The above code works perfectly on the page. However, when I try to open a full view in a video iframe from the same page, the ke ...

Executing Javascript dynamically in VueJS: Learn how to run code from a string efficiently

Currently, I am developing a website with VueJS that enables selected users to upload scripts for automatic execution upon page load. For instance, here is an example of the type of script a user may input: <script src="https://cdnjs.cloudflare.com/aja ...

Refresh the page to change the section using vue.js

I am currently working on a website using Laravel and Vue.js. I require two separate sections for the site: Site: https://www.example.com Admin: https://www.example.com/admin Within the resource/js/app.js file, I have included the main components as fo ...

The SEMrush API is not displaying an 'Access-Control-Allow-Origin' header on the requested resource

When attempting to utilize the SEMrush API, I made a request using jQuery as shown below: $(document).ready(function() { $.get( 'https://api.semrush.com', { type: 'phrase_this', key: ' ...

When utilizing jQuery.Mockjax to simulate the JSON data, the Backbone.Collection.fetch() function consistently results in a 404 error

My setup is pretty straightforward: Main.js: (function($) { "use strict"; var Company = Backbone.Model.extend({ defaults: { title: "", description: "" }, initialize: function() { ...

Exploring and retrieving JSON objects in multidimensional arrays

I'm facing a challenge with the code snippet provided below. var employees = [ { firstName: "John", lastName :"Doe", qualification: {Diploma: 'IT Software' , Degree: 'Software Engineering'} }, { firs ...

What is the process to turn my function into a promise?

Can someone help me "promisify" my custom function located in a different directory? Here is the code snippet: // app.js // include database var mongo = require('./mongo'); var promise = require('bluebird'); var u = require('./ut ...

Detecting the existence of a scrollbar within the document object model using JavaScript - a guide

Could someone provide a JavaScript syntax for detecting the presence of a scrollbar in the DOM by measuring the body height and window height? ...

Initiating Database Countdown (date)

My goal is to create a live countdown timer that updates based on the date retrieved from a MySQL database, without the need for manual refreshing. Here's the code snippet: <?php $date = strtotime($row_tournaments['date']); $re ...

When the mouse is clicked, display the date field; and when a date is chosen,

I have a date displayed as plain text. When I click the 'change' button, a datepicker should appear below it. After selecting a date, the datepicker should be hidden and the date in the plain text should be updated accordingly. <span id="disp ...

The module "myApp" could not be created because of an error: [$injector:nomod]

Encountering an issue with this code. Unsure why I am using angularjs 1.7.x version. $(document).ready(function () { $('#signupBtn-spinner').hide(); var app = angular.module('myApp', []); $('#signupBtn').click(si ...

During the execution of the Promise.map function, the .then() block experienced receiving null before the nested

Initiating a nested promise mapping that is causing the outer .then() block to display a null result before the resolve function is invoked. It seems like there might be an issue with the syntax. Here's a simplified example: const Promise = require( ...

Should reports be created in Angular or Node? Is it better to generate HTML on the client side or server side

I have a daunting task ahead of me - creating 18 intricate reports filled with vast amounts of data for both print and PDF formats. These reports, however, do not require any user interaction. Currently, my process involves the following: The index.html ...

Determine the originating page in Next.js that leads to the current page

Imagine a scenario with three pages: A, B, and C. In this setup, it is possible to navigate from page A to C, as well as from page B to C. However, the displayed content on page C will vary depending on the origin page of the navigation. I am curious to ...

Incorporating interactive buttons within Leaflet popups

I'm facing an issue with adding buttons to a Leaflet popup that appears when clicking on the map. My goal is to have the popup display 2 buttons: Start from Here Go to this Location The desired outcome looks like this sketch: ___________________ ...

What is the best way to select multiple items using mongoose?

For instance, consider this list: [ { name: "John" }, { name: "Mike" }, { name: "Homer" }, { name: "Bart" }, { name: "Dmitry" }, { name: "Dan" } ] If I want to select specific objects ...