Vue.js: definir un servicio


84

Estoy viendo Vue.js como una alternativa a Angular y me gusta mucho hasta ahora. Para tener una idea, estoy refactorizando un proyecto Angular existente en un proyecto Vue. Estoy en el punto en el que necesito comunicarme con mi API REST.

En Angular, solía definir un servicio para eso, que se inyectaba en cada controlador que lo necesitaba. Vue no parece conocer la construcción de "servicio" como yo lo entiendo. ¿Cómo se puede lograr esto en Vue?

Lo consideré vue-resource, pero es solo para las funcionalidades http hasta donde tengo entendido. Como también uso jQuery, esto es obsoleto.

Ejemplo:

Tengo vueComponent1y vueComponent2. Ambos necesitan acceso al mismo recurso REST. Para manejar esto, quiero un servicio central, que ambos componentes puedan usar para solicitudes al recurso REST. Angular tiene el componente 'servicio', que hace exactamente eso. Vue no lo ha hecho.


Proporcione un ejemplo concreto de lo que necesita. http es suficiente para comunicarse con REST
gurghet

Eche un vistazo a vue-resource: github.com/vuejs/vue-resource
nils

Respuestas:


96

De la documentación de Vue.js.

Vue.js en sí no es un marco completo, se centra solo en la capa de vista.

Como biblioteca que se centra en la V de MVC, no proporciona cosas como servicios.

¿Está utilizando algún tipo de cargador de módulos como Browserify o Webpack?
Luego, puede aprovechar el sistema de módulos de ES6 para crear un servicio usted mismo.
Todo lo que tiene que hacer es crear una clase JavaScript simple que este nuevo módulo está exportando.

Un ejemplo podría verse así:

export default class RestResource {

  sendRequest() {
    // Use vue-resource or any other http library to send your request
  }

}

Dentro de su componente vue 1 y 2, puede usar este servicio importando la clase.

import RestResource from './services/RestResource';

const restResourceService = new RestResource();

restResourceService.sendRequest();

2
Gracias por la cotización. Esto significa que no hay estructura ni nada debajo de la vista y el modelo. Si quiero tener un servicio, necesito construir uno propio, por ejemplo, usando JS puro.
Herr Derb

Recibo movieslist.vue?1be4:38Uncaught TypeError: _resource.Resource is not a constructorcuando uso esto ...
George Katsanos

13
Le falta una diferencia significativa con respecto a lo que esperaría con un fondo angular. En este caso, se
crea

1
Sí, obtienes múltiples instancias del mismo servicio de esta manera. Eso no es un problema cuando solo realiza una solicitud Ajax (simplemente ineficiente), pero cuando usa el servicio para su modelo de datos, debe crear una instancia donde declare el servicio y solo exportar la instancia.
mcv

3
Si desea un servicio singleton de 'estilo angular', puede simplemente crear una instancia de esta clase en algún lugar de su aplicación, exportarla export const restResourceService = new RestResource();y luego importarla donde desee. Sin embargo, esto realmente está creando una solución a un problema que hemos creado nosotros mismos, ¿por qué no usar una función? export function sendRequest() { // Make the request } Finalmente, tenga en cuenta que ni siquiera necesita necesariamente una biblioteca para realizar una solicitud http; dependiendo de los requisitos de su proyecto, simplemente podría usar la fetchAPI de JavaScript .
Will Taylor

21

De la documentación de Vue.js sobre cómo crear aplicaciones a gran escala .

La comunidad ha contribuido con el complemento vue-resource , que proporciona una manera fácil de trabajar con las API RESTful. También puede utilizar cualquier biblioteca Ajax que desee, por ejemplo, $ .ajax o SuperAgent .

Vue no requiere que sigas una arquitectura específica, ya que solo se refiere a la capa de Vista en una arquitectura MVC o MVVM. Como ya dijo @Marc en su respuesta , una buena práctica es usar un cargador de módulos como Browserify o Webpack para que pueda crear sus "servicios" en archivos separados, importándolos donde los necesite. Es muy fácil estructurar su aplicación con un cargador de módulos usando vue-cli .

De hecho, personalmente me gusta mucho la arquitectura Flux para aplicaciones basadas en componentes, luego te recomiendo que eches un vistazo a Vuex , una arquitectura de aplicaciones inspirada en Flux que está diseñada específicamente para administrar el estado dentro de las aplicaciones Vue.js.

De esta manera, puede crear acciones que usan vue-resource para solicitar su API, luego puede enviar mutaciones cuando llegan los datos, con todos los componentes que necesitan esos datos ya vinculados al estado global, reaccionando automáticamente. En otras palabras, sus propios componentes no necesitan llamar a los servicios, simplemente reaccionan a los cambios de estado enviados por mutaciones.


4
Solo una nota de que vue-resource ya no se recomienda oficialmente. fuente
interruptor de luz05

1
Echa un vistazo a los detalles: El retirarse vue-recurso escrito por Evan Usted
JeffMinsungKim

18

Puede exportar la instancia de una clase para su servicio:

export default new class {
   ...
}

En tu componente, o en cualquier otro lugar, puedes importar la instancia y siempre obtendrás la misma. De esta forma se comporta de manera similar a un servicio Angular inyectado, pero sin usar this.

import myService from '../services/myservice';

Vue.component('my-component', {
  ...
  created: function() {
    myService.oneFunction();
  }
  ...
})

11

Tiene muy buenas respuestas en esta pregunta ¿Cuál es el equivalente de Angular Service en VueJS?

Como dice @Otabek Kholikov allí, tienes 4 opciones:

  1. Servicio sin estado: entonces deberías usar mixins
  2. Servicio completo: use Vuex
  3. Exportar servicio e importar desde un código vue
  4. cualquier objeto global de javascript

En mis proyectos prefiero (4). Me da la máxima flexibilidad y solo tiene las implementaciones que necesito (no traigo, por ejemplo, Vuex y no debería ser estricto con sus reglas y no hay "magia" - todo el código es mío). Tiene un ejemplo de implementación en la Pregunta que mencioné anteriormente.


6

Si no está utilizando un cargador de módulos, puede definir un complemento personalizado . Algún código de ejemplo:

var myPlugin = {
        install: function (Vue, options) {
            //private
            var myPrivateProperty = 'Private property';

            //instance properties and methods
            Vue.prototype.$myPublicProperty = 'Public Property';

            Vue.prototype.$myAddedMethod = function () {
                return myPrivateProperty;
            };
            Vue.prototype._getData = function (url) {
                return url;
            };

            //static properties and methods
            Vue.myStaticProperty = 'My static prop';
            Vue.myStaticMethod = function () {
                console.log('in');
            }
        }
    };

    Vue.use(myPlugin);

    new Vue({
        el: '#app',
        created: function () {
            //using instance
            console.log(this.$myAddedMethod());
            console.log('my get data: ' + this._getData('some url'));
            console.log(this.$myPublicProperty);

            //using static
            console.log(Vue.myStaticProperty);
            Vue.myStaticMethod();
        }
    });

También puede conectar otras bibliotecas, esta publicación muestra cómo conectar axios.js


1

Puede configurar el recurso vue globalmente como

Vue.http.options.root = "your base url"

y ahora, en cada llamada http, simplemente puede llamar por el nombre del recurso:

this.$http.get('');
this.$http.get('users')
Al usar nuestro sitio, usted reconoce que ha leído y comprende nuestra Política de Cookies y Política de Privacidad.
Licensed under cc by-sa 3.0 with attribution required.