Мы должны использовать согласованное значение по умолчанию для имени контроллера директив компонента, когда он прикреплен к области. См. https://github.com/angular/angular.js/issues/10007#issuecomment -166704255.
В настоящее время мы по умолчанию используем каноническое имя компонента. Это не идеально, так как
а) имена компонентов могут стать длинными и громоздкими для использования в шаблоне
б) сложнее автоматически обновлять шаблон для использования в Angular 2, где контекстом является контроллер.
Критерии для имени следующие:
1) он должен быть одинаковым для всех компонентов
2) он должен начинаться с $
3) оно должно быть коротким (2-4 символа)
Кроме того, имя должно представлять то, что на самом деле публикуется в области видимости.
Некоторые из предыдущих предложений включают:
vm
— это обычно используемое имя во многих приложениях, но контроллер не обязательно является «моделью представления».$comp
— это текущее предложение от команды, но его можно спутать со сравнением, и оно не такое короткое.$ctrl
— это можно спутать с элементами управления вводом$this
— контроллер на самом деле не this
в шаблоне, поскольку контекст по-прежнему является областью действия.c) у программистов возникает соблазн использовать isolate:false
и напрямую обращаться к предкам-контроллерам.
@drpicox - у меня возникает соблазн сказать, что мы запрещаем isolate: false
для компонентов, созданных с помощью этого помощника.
Я согласен, после рассмотрения этого:
isolate: true
, когда ограничение равно 'E': для меня они действительно являются компонентами, где нотация $ctrl имеет полное значениеisolate: false
при ограничении 'A': для меня это _decorators_, своего рода энхансер существующих компонентов, в этом случае $ctrl сталкивается, так что текущая номенклатура в порядкеНо я считаю, что во втором случае лучше обойтись директивами, _декораторы_ встречаются нечасто, обычно низкого уровня и не подходят для юниоров.
Так что, наверное, неплохо забанить isolate: false
.
В другом направлении мышления, о _decorators_, функция для получения контроллера компонента «E» текущего объекта должна быть хорошей идеей, особенно для написания общих _decorators_ для работы с любым текущим компонентом (требуются силы, чтобы заранее знать, какой контроллер есть, и вы не можете использовать тот интерфейс, который вы ищете).
Мне нравится $cmp
, но $comp
еще лучше, потому что он понятнее.
Мне нравится
$cmp
, но$comp
еще лучше, потому что он понятнее.
Мне нравится $comp
. Всякий раз, когда я вижу $cmp
, я думаю «сравнить».
другое предложение: почему бы не использовать имя компонента в качестве имени экземпляра контроллера?
например: профиль пользователя -> scope.userProfile
@tabanliviu Вот как это сейчас делается на master
, но @petebacondarwin упомянул в этом же выпуске, в первом посте, почему обычное имя лучше.
@mgol :+1: Кажется, я упустил это из виду, когда читал билет. Следует ли считать это изменение скорее проблемой ngUpgrade? Я думаю, что в контексте angular 1.x текущая реализация является хорошим решением. Возможно, выставить это как функцию настроек, которая берет имя компонента и выводит имя контроллера? таким образом он обслуживает текущий шаблон и будущий путь миграции.
Время велопарковки.
+1 за $ctrl.
Ctrl имеет много ранее существовавших культур в документации Angular 1 и примеров в качестве суффикса «контроллер». Попробуйте погуглить "угловой Ctrl" для хорошей меры.
Текущий выбор получения его из имени компонента довольно неприятный, поскольку они действительно имеют тенденцию быть довольно длинными в реальных приложениях.
:+1: для $ctrl
$vm
по умолчанию больше похоже на заявление о том, как следует использовать контроллеры.
+1 за $ctrl
.
Мы активно обсуждали это в команде ng-forward и решили, что ctrl
менее нагруженный термин, чем vm
.
Я голосую за $ctrl
, и я был бы очень рад, если бы это побудило людей больше не называть свои контроллеры vm
:P
О, я бы еще добавила
это можно спутать с элементами управления вводом
Неа. Не совсем.
$ctrl
Я думаю, что это было бы наиболее понятным и интуитивно понятным для всех.
+1 $ctrl
Другие предложения:
Я голосую за $this
, потому что в ng2 this
контроллера является контекстом шаблона (и, на мой взгляд, component
очень хорош в роли инструмента перехода между ng1 и ng2).
+1 за $ctrl
Я также предпочитаю свойство $ctrl
, потому что оно представляет контроллер компонента.
+1 за $ctrl
+1 за $это
Я бы даже пошел с this
и отказался от $
, если бы это не было слишком сложной задачей. Кроме того, это единственный вариант, который не является сокращением от чего-то еще, а я ненавижу аббревиатуры. :)
Я бы выбрал $ctrl или $cc (это сокращение от контроллера компонентов)
+1 за $ctrl
Мы могли бы назвать это просто $troll
, в нем есть немного $this
и половина от $controller
. Нет, шучу, меня устраивает $ctrl
. :+1:
$ Ctrl + 1
$вм
Плюсы
Минусы
$ctx
— сокращение для контекста.
Более общий, чем $ctrl
, менее анонимный, чем $vm
, не вводящий в заблуждение, как $comp
или $this
.
Я посмотрел на механизмы шаблонов (Jade, Handlebars, Mustache.js, Dust.js, Nunjucks, EJS и т. д.), и мне кажется, что имена context
, locals
или data
используются для имени переменной, передаваемой методу рендеринга.
Кроме того, $ctx
, для контекста, не имеет такой же когнитивной перегрузки, как $ctrl
(или $this
), и, действительно, вы сказали in Angular 2, where the context is the controller
.
@albertosantini - одна проблема с $ctx
заключается в том, что фактический контекст - это текущая область, которая также доступна напрямую через this
.
$vc
— расшифровывается как View Controller.
я нашел ссылку в документах Apple
"...Класс UIViewController определяет методы и свойства для управления вашими представлениями, обработки событий..."
Я решительно голосую за $this
:
<textarea ng-change="$this.handleChange">
_Плюсы:_
ctrl = this
внутри вашего контроллера, чтобы обе сущности выглядели одинаково.$this
, кажется, что Angular представляет даже _"более проприетарный язык"_, что является одной из популярных жалоб на Angular . Ваш контроллер будет загрязнен следующим образом: controller: function() {
var ctrl = this;
ctrl.items = [];
ctrl.text = '';
ctrl.handleSubmit = function () {
ctrl.items.push({text: ctrl.text});
ctrl.text = '';
};
}
вместо более чистого, элегантного и независимого от фреймворка
controller: function() {
this.items = [];
this.text = '';
this.handleSubmit = function () {
this.items.push({text: this.text});
this.text = '';
};
<textarea onChange={this.handleChange}>
@dmitriz Одна проблема с $this
в AngularJS заключается в том, что в шаблоне контекст (то есть this
) на самом деле не является контроллером. Кажется, что в React (и Angular 2) это действительно одно и то же, поэтому имеет смысл использовать this
(или $this
). В Angular 1 они не совпадают, поэтому $this
может вызвать еще большую путаницу.
Что касается JavaScript, в коде ES5 очень часто используется псевдоним this
для чего-то еще из-за проблем с привязкой this
при вызове бесплатных методов. Таким образом, контроллеры все равно часто будут иметь что-то вроде var that = this
, и в этом случае можно также использовать var ctrl = this
.
При этом нет необходимости делать это в ваших контроллерах, если вы этого не хотите. IMO вполне разумно использовать this
внутри объекта, но затем ссылаться на объект под каким-либо другим именем при использовании его извне.
@dmitriz , вам не обязательно иметь один и тот же псевдоним в контроллере и в представлении (я никогда этого не делаю). Кроме того, я всегда использую var self = this
в контроллере, чтобы не использовать .bind(this)
для обратных вызовов и т. д.
Так что это не должно быть проблемой, имхо.
Относительно других вариантов:
$ctx
: мне это не нравится, потому что (как упоминал @petebacondarwin ) контроллер не является контекстом выражений.$this
: мне это не нравится, потому что (в выражениях Angular) this
— это специальный псевдоним для текущей области, поэтому наличие this --> scope
и $this --> controller
было бы еще более запутанным. (В противном случае мне бы это понравилось.)$vm
: мне это не нравится (по уже упомянутым причинам), но я могу согласиться с этим, если ничто лучше не соответствует нашим ограничениям.$cmp
: Не суперудовлетворительно (потому что не на 100% точно), но достаточно декларативно. Мог бы пойти с этим, если ничто лучше не соответствует нашим ограничениям.$comp
: я предпочитаю $cmp
, потому что он короче (и я не нахожу его более «способным спутать» с compare
, чем с $comp
).$ctrl
: Мне это очень нравится. Он довольно короткий, декларативный и настолько точный, насколько это возможно. Я всегда добавлял к своим контроллерам суффикс ctrl
и никогда не видел путаницы с ConTRoL
(но более знающие люди утверждают, что путаница была :)). Если мы решим, что путаница не является проблемой, я определенно выберу это, но меня устраивает и что-то другое.$troll
: Нужно еще подумать. У него определенно есть потенциал :stuck_out_tongue:$as
, $at
, $cc
, $prox
, $vc
): я думаю, что они вводят новые концепции и будут более сбивает с толку, чем помогает.Я голосую за $ctrl
, потому что это _является_ контроллером директив. Простой.
Против остальных:
$vm
-- Как уже указывалось, это не обязательное намерение использования => либо путаница в чтении шаблона/кода, либо меньший выбор для разработчика (вынужден реализовать vm)$cmp
-- Ну не сам компонент, а (только) контроллер? Так на самом деле вводят в заблуждение?$this
-- Также уже упоминалось, что это сбивает с толку. Что делает экземпляр контроллера «этим» в области видимости? Семантически я не вижу, что это может быть... ну... понятно?$ctx
-- Фактически то же самое, что и $this
.Также, как уже сказал Паскаль: я не вижу путаницы с элементами управления. Если Angular2 не внедряет все элементы DOM/input таким образом (например, $ctrl, $val, $cmbx и т. д.), я не вижу в этом проблемы.
+1 $ctrl
В той же строке, что и предыдущие комментарии:
$vm
, $as
, $at
, $cc
, $prox
, $vc
, $ctx
,. ..: вводит программистам новые ненужные понятия$this
: поскольку this
уже существует, это может сбить с толку программистов.$cmp
или $comp
: (лучше сначала) это должно быть хорошо, потому что это фокусирует программистов на компонентной модели, но они могут быть не прямолинейными$ctrl
: это то, что публикуется в области действия, контроллере, поэтому кажется, что это действительно ясно, легко понять и использовать.Понятно, спасибо за уточнение, я не знал this = $scope
, но да, это исключает.
Тогда $ctrl
звучит как следующий лучший выбор, если не считать $troll
:)
+1 за $ctrl
: самый интуитивно понятный и самый общий
@petebacondarwin Спасибо за подробности.
Так что +1 за $ctrl
.
Я предпочитаю декларативное $ctrl
в качестве имени по умолчанию.
@petebacondarwin @PascalPrecht
Почему VM не является хорошим представлением?
(Если вы уже обсуждали это по другому вопросу, просто дайте ссылку, если можете)
Поскольку, насколько мне известно, контроллеры в Angular ближе к моделям просмотра, чем к классическим контроллерам из MVC. но может я что-то упускаю.
Я согласен с точками @QuinntyneBrown -
это короче.
но важнее -
Руководство по стилю @johnpapa очень популярно, и многие люди, которых я знаю, ссылаются на него как на часть своей программы обучения «новых разработчиков».
Если мы изменим это здесь, мы должны рассмотреть, как это повлияет на новых разработчиков (возможно, отправить PR в руководство по стилю).
Вот почему мне нравится более короткое имя «$vm» (кстати, почему оно должно начинаться с $
? :)
(Кстати, почему он должен начинаться с $? :)
Имена, определенные в Angular, начинаются с $
, когда они разделяют пространство имен с определениями программиста, это позволяет избежать коллизий. В этом случае он определяется Angular и определяется внутри области видимости, где программист может иметь свои собственные определения. Используя $
, мы избегаем конфликта имен, и Angular ведет себя в соответствии с ожиданиями программистов.
(@johnpapa) Цель этого руководства по стилю — предоставить руководство по созданию приложений Angular, показав соглашения, которые я использую, и, что более важно, почему я их выбираю.
Стиль Y032 Используйте для этого переменную захвата при использовании синтаксиса controllerAs. Выберите согласованное имя переменной, например vm, что означает ViewModel.
Таким образом, не имеет значения, vm
, ctrl
или troll
, это просто должна быть непротиворечивая переменная.
Кроме того, как я указывал ранее, идея не в том, чтобы добавлять новые понятия: vm
означает ViewModel
, если вы не используете View Models или не знакомы с ним, вы не поймете что означает vm
или ViewModel
, что может сбить с толку.
Я не любитель путать имена. Я думаю, что ctrl
сбивает с толку. Это контроллер? управление (например, управление html)? и разве это не для компонента?
Я голосую либо за vm
, либо comp
. vm
обычно используется и легко объяснимо. comp
новое, но нетрудно угадать.
Как насчет $ctlr
(т.е. ConTroLleR), а не $ctrl
?
+1 $комп.
@petebacondarwin О, сколько дислектиков (таких как я), которые будут бомбить нас вопросами об этом... :)
@drpicox Спасибо за объяснение, я вижу ваши точки зрения, и они верны. это сложно, но я могу поделиться этим, по крайней мере, из своего опыта, у меня не было проблем с обучением разработчиков соглашению «vm», и я помог нескольким компаниям структурировать свои огромные приложения таким образом, они получили это довольно быстро, но, может быть, я м одинок в этом опыте.
Но я понимаю ваши доводы. согласен с $
Я все еще за $vm, но меня устраивает и $comp...
@wesleycho из команды Angular UI Bootstrap, похоже, категорически против vm
:
https://github.com/angular/angular.js/issues/10007#issuecomment -166707284
+1 за $ctrl
@shairez Я полностью разделяю ваше мнение о соглашении, я внештатный архитектор с десятками проектов, соглашение vm
очень помогло, но у меня все еще есть некоторые проблемы. Оказывается, есть люди, сопротивляющиеся его использованию. Вероятно, сопротивление должно быть ниже, если это соглашение исходит от самого Angular, но я уверен, что если бы имя было $ctrl
, они приняли бы его как есть, без какого-либо сопротивления. $ctrl
просто прямо вперед.
Итак, голоса подведены, и это выглядит так:
$comp 4
$cmp 2
$ctrl 19
$vm 3
$this 3
$ctx 2
$vc 1
Явным фаворитом является $ctrl
. Помимо того, что он популярен, он соответствует критериям, опубликованным в начале этого выпуска. Кроме того, он не вводит какой-либо особенно новой концепции. На самом деле речь идет о контроллере (контроллере компонента/директивы), который разработчики Angular уже понимают, и так же, как некоторые разработчики привыкли использовать vm
в своих директивах, разработчики не заставят себя долго ждать.
Круто, $ctrl это!
$ctrl
Еще одна проблема, которую я хотел бы затронуть, заключается в том, что в angular 1.4 и ниже мы не можем использовать «как имена», начинающиеся со знака $
.
Это дает следующую ошибку:
Error: [$controller:ctrlfmt] Badly formed controller string
У некоторых компаний возникают проблемы с обновлением до последних версий, и это может занять несколько месяцев.
Они по-прежнему хотят не отставать от соглашений, поэтому их процесс обновления в будущем будет проще.
Для них переход с vm
на $ctrl
невозможен.
Как вы думаете? какие-либо предложения?
возможно, мигрировать поэтапно:
начните с преобразования vm
в ctrl
когда выйдет версия 1.5, "обновите" ctrl
до $ctrl
Другой возможный способ — хотя и многословный — состоит в том, чтобы сгенерировать псевдоним controllerAs во время выполнения, проверяя angular.version
. что-то типа:
angular
.module('github')
.directive('issueThread', issueThread);
/* <strong i="14">@ngInject</strong> */
function issueThread () {
// this can be required as a module if using some module loader
// or - another way is using global on angular namespace (i know it a bad practice - hwoever just to indicate reuse of this check
let prefix = angular.version.minor === 5 ? '$' : '';
let controllerAs = prefix + 'ctrl';
// with template strings
var controllerAs = `${prefix}ctrl`;
var directive = {
controller: controller,
restrict: 'E'
};
return directive;
function controller() {
}
}
@orizens А как насчет шаблонов?
@shairez Мммм, это имеет смысл, символы $ предназначены только для угловых внутренностей ... может быть, неплохо иметь какую-то прямую совместимость в следующем миноре.
@drpicox , ты прав :).
Опять же, одно решение, которое я могу придумать (хакерское...), это «заменить» ctrl на $ ctrl в шаблоне во время выполнения/сборки. Этого можно легко добиться, если проект построен с использованием es6 и модулей. в противном случае это задача для gulp/grunt/npm во время сборки.
Почему бы просто не использовать controllerAs
?
Это не идеальное решение (и действительно, нам, возможно, придется пересмотреть RegExp, который извлекает идентификатор из строки контроллера (если есть), но использование controllerAs
совместимо как назад, так и вперед :)
(Если кто-то хочет попробовать обновить этот идентификатор, извлекая RegExp, это прямо здесь, кстати.)
@gkalpak , это хороший момент, продвижение вперед по продвижению использования свойства controllerAs
хорошо, поскольку я полагаю, что все больше и больше людей перейдут на использование компонентов в своих версиях 1.4 и более ранних.
Но я думаю, что это может сбить с толку, если мы начнем учить людей $ctrl
, и в некоторых случаях это работает, а в некоторых нет.
Так что прямая совместимость (не знаю как) — отличная идея!
@shairez вы (можете ли вы) создать новую проблему, чтобы отслеживать это?
Я создал # 13736, который позволяет использовать идентификатор $
при использовании <ctrl> as <identifier>
.
Тем не менее разрешенные идентификаторы различаются между controller: '... as ...'
и controllerAs: '...'
.
Тем не менее, я не уверен, что продвижение controller: '... as $ctrl'
— это хороший способ не отставать от условностей. Обновить controller: '... as $ctrl'
намного сложнее, чем controller: '...', controllerAs: '$ctrl'
.
Спасибо @gkalpak - я согласен с тем, что нам, вероятно, следует поощрять использование свойства controllerAs
, а не контроллера в качестве синтаксиса.
Во-первых, в документации компонента говорится: «Определения компонентов очень просты и не требуют такой сложности, как определение общих директив».
Еще одно: контроллер в директиве необходим только в том случае, если вы создаете сложные директивы, взаимодействующие друг с другом. В противном случае функции ссылки более чем достаточно (например, «используйте контроллер, когда вы хотите предоставить API другим директивам. В противном случае используйте ссылку» в директиве Руководства разработчика, и из моего опыта директивы, реализующие ту же функциональность со ссылкой вместо контроллеров, используемых несколько сотен раз в ng-repeat гораздо быстрее.
Так...
Я не нахожу в Component ("простая" директива) способ сделать "простой" (функция ссылки), только тяжелый (контроллер).
Я что-то пропустил?
Спасибо за объяснение.
@frfancha - улучшение производительности связано с тем, что не нужно использовать $injector
для создания экземпляра контроллера, верно? Возможно, у вас есть какие-то измерения производительности, которые вы можете предоставить?
Идея помощника компонента состоит в том, чтобы упростить (в смысле LOC) написание директив типа компонента (изолировать, элемент); и легче писать код, который больше соответствует тому, как все делается в Angular 2.
Если в конкретном приложении есть проблема с производительностью, было бы довольно просто преобразовать директиву компонента для использования более общего помощника directive
.
Я думаю, нам нужно взглянуть на другие документы API и руководства для разработчиков, чтобы убедиться, что они совместимы с новым помощником component()
.
@petebacondarwin Вначале мы писали все наши директивы с помощью контроллера только потому, что так было показано в первом уроке, которому мы следовали.
Только после того, как мы обнаружили, что "открытие" определенной страницы с 1000 директивами (5 по "строкам" в ng-repeat x 200) занимает около 15 секунд, мы прочитали больше о директивах и поняли, что контроллеры бесполезны, если вы не " говорить" между директивами (запрашивая контроллер другой). После «переписывания» всего с линк-функциями вместо контроллеров (переписать — громко сказано, так как это было просто копирование/вставка кода в линк вместо контроллера), время отображения страницы составило 8 секунд.
Обратите внимание, что это меры Firefox, в то время мы не использовали Chrome. Теперь мы используем его, и я оцениваю время в Chrome как треть от Firefox (а использование памяти — четвертое (и без утечки памяти, что здорово, в Firefox наше приложение, как известно, «медленно днем)).
В целом мы очень довольны angular (мы преобразовали все наши приложения для ввода данных из приложения Windows Smalltalk в WEB API + angular (на случай, если вам будет интересно это увидеть? Я иногда бываю в Лондоне).
Но я удивлен выбором контроллера для поддержки «простого способа» сделать директиву
спасибо @gkalpak !
@petebacondarwin отдельная проблема больше не актуальна, верно? (из-за пиара)
Я согласен (как я уже писал), мы должны обучать людей использовать свойство controllerAs, но я только что упомянул об этом, потому что я предсказываю, что люди столкнутся с этим.
Самый полезный комментарий
Итак, голоса подведены, и это выглядит так:
Явным фаворитом является
$ctrl
. Помимо того, что он популярен, он соответствует критериям, опубликованным в начале этого выпуска. Кроме того, он не вводит какой-либо особенно новой концепции. На самом деле речь идет о контроллере (контроллере компонента/директивы), который разработчики Angular уже понимают, и так же, как некоторые разработчики привыкли использоватьvm
в своих директивах, разработчики не заставят себя долго ждать.