Угловые насмешки с минификацией

Миссия:

У меня есть наследие, un-minified Angular 1 app с тысячами тестов, все проходящие. Я ввел в код минимизацию и искажение. Если я сохраню libs и код приложения отдельно, тесты продолжат работать. Тем не менее, я не могу исказить код приложения, потому что это приведет к разрыву контракта обратно в файлы libs.

Я хочу иметь возможность искажать код приложения и поддерживать работу модульных тестов.

текущее состояние:

Я создал два пути, чтобы обойти проблему, но я не удовлетворен, потому что модульные тесты на самом деле не попадают в код, который будет в производстве… они попадают в середину, созданную, чтобы избежать проблемы искалечивания.

Путь 1

Один путь выводит a libs.min.jsи an app.min.js. Внутри libs.min.jsесть такие вещи, как Angular, Undersorce и так далее — используя их предоставленные уменьшенные версии. По сутиlibs.min.js, это просто куча уже уменьшенных файлов, объединенных вместе. app.min.jsсодержит наш код приложения, уменьшенный, но не искаженный.

Путь 2

Второй путь создает combined.min.jsфайл. Это то, что идет в производство. Внутри этого файла, в порядке, угловые, подчеркивания и так далее, а затем наш код приложения. Все они объединены в этот файл unminified (в том числе libs), а затем искалечены/minified вместе, так что мы получаем одну исходную карту, которая может ссылаться на наш код приложения, а также код библиотеки. Это работает в браузере, но модульные тесты прерываются, потому combined.min.jsчто не включает требуемую библиотеку только для тестирования angular-mocks.

Проблема:

Тестирование по пути один работает, потому что Karma загружает эти файлы. Это хорошо, но это не фактический код, который будет производиться, поэтому я не считаю это победой.

  1. библиотеки.минута.js
  2. angular-mocks (unminified — и может привязываться к Angular, потому что мы используем предоставленную уменьшенную версию)
  3. приложение.минута.js (minified, но не mangled, потому что mangling нарушает контракт обратно к libs.минута.js)
  4. *.спекуляция.js

Второй путь тестирования не работает, потому что мы загружаем вещи в следующем порядке:

  1. комбинированный.минута.js
  2. angular-насмешки (unminified)
  3. *.спекуляция.js

Бум. Наш код приложения уже подключил свои привязки, поэтому angular-mocks слишком поздно. Я не вижу никакого способа обойти это, кроме загрузки libs и приложения в отдельные файлы, как в path one.

Некоторые тесты проходят, но те, кто пытается ссылаться на что-либо, на что мы полагаемся, угловой-насмешки для неудачи.

Я знаю, что могу предоставить карту источника вводаapp.min.js, чтобы я мог уменьшать/искажать код приложения отдельно (но последовательно противlibs.min.js), но я не уверен, что это лучший маршрут. Я хотел бы сохранить все в одном большом файле, но если нет другого способа, это выглядит как библиотека, которую я использую, чтобы искалечить/minify (UglifyJS) поддерживает входные исходные карты…

О. Кроме того, мы не используем ворчание или глоток. Просто прямой NPM, чтобы сделать все это. Но если есть библиотека ворчания или глотка, которая каким-то образом решает это, я могу NPM-ify это.

1 ответ

  1. Я понял это. Первоначальный вопрос не совсем верен в своем диагнозе того, что было неправильно. Сомневаюсь, что кто-то еще наткнется на такую проблему, но оставлю ее здесь на всякий случай.

    Проблема 1:

    Сокращая библиотеки и приложения Вместе, мы потребовали, чтобы некоторые библиотеки работали в строгом режиме, который изначально не был в строгом режиме. Либо они не находятся в самоисполняющейся функции, либо есть глобальная утечка «use strict» из какой-то другой библиотеки… есть много причин, почему это может произойти.

    В моем случае преступник был Рестангулярным. Версия 1.4 не будет работать в строгом режиме, потому что есть неявное определение ‘data’. Я уверен, что это оплошность в старой версии, но тем не менее это вызовет ошибки в Phantom об «отсутствии такого свойства»данные»».

    Это легко исправить. Скорее всего, просто обновите до более новой версии. Обновление до более новой версии не допускается для этого приложения, поэтому сейчас я просто вручную добавил «var data», чтобы обмануть определение.

    Задача 2:

    Наши тесты жасмина начинают проваливаться. Однако они выполняют и потребляют уменьшенный код. Пример того, что произошло при запуске с уменьшенным кодом:

    var result,
        someObject = {foo: "bar"};
    
    httpBackend.whenGET("/something").respond(someObject);
    
    somethingService.then(function(response) {
       result = response;
    });
    
    httpBackend.flush();
    
    expect(result).toBe(someObject);  // fail.  {foo: "bar"} is not {route: "something", getRestangularUrl: function...}
    

    Обычно это работает, потому что ngMocks обходит оболочку ответа Restangular; объект, с которым вы отвечаете, будет передан разрешенному обещанию без добавления метаданных Restangular. Так {foo: "bar"}остается собственно {foo: "bar"}.

    Но, так как мы загрузили ngMocks после нашего кода приложения (см. «путь 2» в вопросе), ответ Restangular больше не обходится. Таким образом, Restangular расширяет предполагаемый ответ со всеми дополнительными метаданными.

    Таким образом , наш {foo: "bar"}становится целым Рестангулярным ответом, который содержит {foo: "bar"}, но который не только {foo: "bar"}.

    Разрешение: не тестируйте весь объект. Проверьте наличие определенного ключа и его значение.

    var result;
    
    httpBackend.whenGET("/something").respond({foo: "bar"});
    
    somethingService.then(function(response) {
       result = response;
    });
    
    httpBackend.flush();
    
    expect(result.foo).toEqual("bar");  // pass
    

    Я бы сказал, что тестирование таким образом лучше, так как это более точное представление о том, что на самом деле произойдет, когда ngMocks исчезнет в любом случае.