Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Example of injecting services in Angular 1.5 components

Tags:

angularjs

Can anyone give an example on using services with Angular 1.5 components?

I'm trying to inject a service in an Angular 1.5 component, but it doesn't work.

I have a login component like so:

class Login {
    constructor($scope, $reactive, $state, myService) {
        console.log(myService.somevariable); //doesn't work
    }
}

// create a module
export default angular.module(name, [
    angularMeteor
]).component(name, {
    templateUrl: 'imports/ui/components/${name}/${name}.html',
    controllerAs: name,
    controller: Login
});

My service looks like this:

angular.module(name).service("myService", function () {
    this.somevariable = 'somevalue';
});

I just cant seem to be able to get the service injected in the component.What am I doing wrong?

SOLUTION:

With sebenalern's help, I got it working.

I needed a service to validate an email address using a regular expression. I did it like this:

import angular from 'angular';
import angularMeteor from 'angular-meteor';
class Validator { 
    validateEmail(email) {
        var re = /^(([^<>()\[\]\\.,;:\s@"]+(\.[^<>()\[\]\\.,;:\s@"]+)*)|(".+"))@((\[[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}])|(([a-zA-Z\-0-9]+\.)+[a-zA-Z]{2,}))$/;
        return re.test(email);
    }
}

const name = 'validator';

// create a module
export default angular.module(name, [
    angularMeteor
])

.service("Validator", Validator);

I then injected the service like so:

import {name as Validator} from '../../../api/services/validator'

class Login {
    constructor($scope, $reactive, $state, Validator) {
        'ngInject';
        this.$state = $state;

        $reactive(this).attach($scope);
        this.Validator = Validator;
    }

    login() {
        if(this.Validator.validateEmail(this.credentials.email)) {
            // email is valid. 
        }
    }    
}

const name = 'login';

export default angular.module(name, [
    angularMeteor,
    Validator
]).component(name, {
    templateUrl: `imports/ui/components/${name}/${name}.html`,
    controllerAs: name,
    controller:Login
})

Hope this helps :)

like image 275
lostsoul29 Avatar asked Apr 16 '16 00:04

lostsoul29


People also ask

What is injectable () in Angular service?

The @Injectable() decorator defines a class as a service in Angular and allows Angular to inject it into a component as a dependency. Likewise, the @Injectable() decorator indicates that a component, class, pipe, or NgModule has a dependency on a service. The injector is the main mechanism.

How many ways we can inject service in Angular?

There are three types of Dependency Injections in Angular, they are as follows: Constructor injection: Here, it provides the dependencies through a class constructor. Setter injection: The client uses a setter method into which the injector injects the dependency.

Are components injectable in Angular?

A component is injectable by default @Component() (or @Directive() ) includes @Injectable() . Don't expect to get a specific instance of a component injected. This works for example with constructor(@Host() private parentComponent) where DI lookup is limited to parent injectors up to the injector of the host element.

What's the best way to inject one service into another in Angular?

Use the @Injectable() decorator on any service that depends on another. Inject the other services into the constructor of the dependent service.


1 Answers

So one problem I see is you should be using the keyword this inside the constructor

this.$scope = $scope;

Another thing it is probably easier to stay away from classes and use functions:

class Login {
constructor($scope, $reactive, $state, myService) {
    console.log(myService.somevariable); //doesn't work
   }
}

Becomes:

angular
.module('name')
.service('myService', myService);

function myService () {
    this.somevariable = 'somevalue';
}

To me it seems a lot cleaner. Also another thing about ES6 classes is

ES6 Classes are not hoisted, which will break your code if you rely on hoisting

For more info see link.

Now here is the working code I came up with:

First we declare the module:

angular.module('name', []);

Next we register our service and then create the service definition:

angular
   .module('name')
   .service('myService', myService);

function myService () {
   this.somevariable = 'somevalue';
}

Next we do the same procedure for our controller and also we inject $scope and our service into it.

angular
   .module('name')
   .controller('Login', Login);

function Login($scope, myService) {
    $scope.someVar = myService.somevariable;
}

Last I registered our component:

angular
   .module('name')
   .component('my-html', {
   templateUrl: 'my-html.html',
   controller: Login
});

And that is it on the javascript side.

Here is my html code:

<!DOCTYPE html>
<html lang="en-us" ng-app='name'>
  <head>
      <script src="//code.angularjs.org/1.5.0-rc.1/angular.js"></script>
      <script src="controller.js"></script>
  </head>
  <body >
      <h ng-controller="Login">{{ someVar }}</h>
  </body>
</html>

I hope this helps!!

like image 63
sebenalern Avatar answered Sep 28 '22 02:09

sebenalern