Angular.js: Czy .value () to właściwy sposób ustawiania stałej aplikacji i pobierania jej w kontrolerze

87

Cześć, oglądałem kilka filmów angular.js i zauważyłem, że metoda value () została użyta do ustawienia stałej dla całego modułu. na przykład można ustawić konfigurację biblioteki Angular-UI w następujący sposób: (coffeescript)

angular.module('app',[])
.value "ui.config", 
  tinymce:
    theme: 'simple'
    width: '500'
    height: '300'

A moja aplikacja wygląda obecnie tak:

window.app = angular.module("app", [ 'ui'])

.config(["$routeProvider", ($routeProvider) ->
  $routeProvider
  .when "/users",
    templateUrl: "assets/templates/users/index.html"
    controller: IndexUsersCtrl

  .otherwise redirectTo: "/users"

])

.value 'csrf', $('meta[name="csrf-token"]').attr('content') #<---- attention here

IndexUsersCtrl = ($scope) ->
  $scope.users = gon.rabl
  console.log "I want to log the csrf value here" #<---- then attention
IndexUsersCtrl.$inject = ['$scope']

Ale wydaje mi się, że nie mogę uzyskać tej wartości, dotykając zmiennej „app”, która odpowiada modułowi aplikacji.

Czytałem tutaj w ST i dalej w grupie Google angularjs, że jednym ze sposobów udostępniania wspólnego kodu między kontrolerami jest usługa, czy ta koncepcja będzie miała zastosowanie również tutaj?

Dzięki!

Nik So
źródło
3
Jeśli nie jesteś tego świadomy, usługa $ http ma pewne możliwości CSRF. Zobacz sekcję „Ochrona przed fałszerstwami między witrynami (XSRF)” tutaj: docs.angularjs.org/api/ng.$http
Mark Rajcok

Odpowiedzi:

147

Module.value(key, value)służy do wstawiania edytowalnej wartości, Module.constant(key, value)służy do wprowadzania stałej wartości

Różnica między nimi nie polega na tym, że „nie można edytować stałej”, chodzi raczej o to, że nie można przechwycić stałej za pomocą $ dostarczyć i wstrzyknąć coś innego.

// define a value
app.value('myThing', 'weee');

// define a constant
app.constant('myConst', 'blah');

// use it in a service
app.factory('myService', ['myThing', 'myConst', function(myThing, myConst){
   return {
       whatsMyThing: function() { 
          return myThing; //weee
       },
       getMyConst: function () {
          return myConst; //blah
       }
   };
}]);

// use it in a controller
app.controller('someController', ['$scope', 'myThing', 'myConst', 
    function($scope, myThing, myConst) {
        $scope.foo = myThing; //weee
        $scope.bar = myConst; //blah
    });
Ben Lesh
źródło
4
jak token „myService” pasuje do obrazu?
Dave Edelhart
1
@DaveEdelhart, Przepraszam, że nie widziałem wcześniej twojego pytania. Miałem go tam jako przykład usługi, która wykorzystała tę wartość. Na szczęście Pavel Hlobil jest dobrym Samarytaninem i dodał adnotację do mojego kodu, aby było jaśniej.
Ben Lesh
2
Nie, to nie jest „tylko do odczytu”. Gdybyś umieścił tam obiekt, wszystko mogłoby zmienić jego właściwości. Dzieje się tak głównie dlatego, że jest to JavaScript, a nie ze względu na szczególne problemy projektowe ze strony Angulara. Jednak nie widziałem wartości używanej w taki sposób, że jest ona zmieniana, zwykle widziałem, jak jest używana do wstrzykiwanych „stałych”.
Ben Lesh,
2
Jednak stałe NIE są niezmienne. Po prostu nie możesz ich nadpisać kolejnym zastrzykiem, ponieważ $ dostarcza ich nie przechwyci do dekoracji.
Ben Lesh,
2
Wiem, że to stara odpowiedź, ale „Module.value (klucz, wartość) jest używany do wstrzyknięcia edytowalnej wartości, Module.constant (klucz, wartość) jest używany do wstrzyknięcia stałej wartości” nie zgadza się z ng w swoim ostatnie wcielenie (1.3.4). Różnica między module.value () a module.constant () jest taka, że: stała () jest dostępna na wcześniejszym etapie cyklu życia aplikacji (podczas konfigurowania i uruchamiania); value () jest dostępna tylko podczas uruchamiania. To, czy są one zmienne i gdzie zmienione wartości są widoczne, zależy od struktury ich wartości (prymitywnej lub nie). docs.angularjs.org/guide/providers#constant-recipe
lukkea
4

Niedawno chciałem użyć tej funkcji z Karmą w teście. Jak zauważa Dan Doyon, kluczem jest to, że należy wstrzyknąć wartość, tak jak kontroler, usługa itp. Możesz ustawić .value na wiele różnych typów - ciągi, tablice obiektów itp. Na przykład:

myvalues.js plik zawierający wartość - upewnij się, że znajduje się on w Twoim pliku konfiguracyjnym karmy

var myConstantsModule = angular.module('test.models', []);
myConstantModule.value('dataitem', 'thedata');
// or something like this if needed
myConstantModule.value('theitems', [                                                                                                                                                                                                             
  {name: 'Item 1'},                                                                                                                                                                                                                         
  {name: 'Item 2'},                                                                                                                                                                                                                         
  {name: 'Item 3'}
]);                                                                                                                                                                                                                         

]);

test / spec / mytest.js - być może jest to plik specyfikacji Jasmine załadowany przez Karmę

describe('my model', function() {
    var theValue;
    var theArray;
    beforeEach(module('test.models'));
    beforeEach(inject(function(dataitem,theitems) {
      // note that dataitem is just available
      // after calling module('test.models')
      theValue = dataitem;
      theArray = theitems;
    });
    it('should do something',function() {
      // now you can use the value in your tests as needed
      console.log("The value is " + theValue);
      console.log("The array is " + theArray);
    });
});
Migawka
źródło
2

Musisz odwołać się csrfdo swojego kontroleraIndexUsersCtrl = ( $scope, csrf )

IndexUsersCtrl.$inject = [ '$scope', 'csrf' ]
Dan Doyon
źródło