30

We currently have an existing small Angular 1 project that is used in an on premises Sharepoint 2013 environment. For a large part of our content, we use publishing pages on the Sharepoint environment.

With Angular 1, we could define directives to be restricted to: match attribute name, tag name, comments, or class name. Most of the directives we created were attribute or tag name. The preference would have been tag name, but the publishing platform on Sharepoint strips out unknown elements. So that means we were left with using attributes in order to bring our directives in to the publishing pages. With Angular 2 though, I've only seen components implemented by tag name.

Is it possible with Angular 2 to use attribute names in order to use our components? This is a requirement for us because of the restrictions in the Sharepoint publishing platform.

Thanks.

random_user_name
  • 25,694
  • 7
  • 76
  • 115
TehOne
  • 2,569
  • 3
  • 26
  • 36

4 Answers4

55

Yes, the selector property of the @Component decorator is a CSS selector (or a subset of):

selector: '.cool-button:not(a)'

Specifies a CSS selector that identifies this directive within a template. Supported selectors include element, [attribute], .class, and :not().
Does not support parent-child relationship selectors.

Source: Angular Cheat Sheet / Directive Configuration, which @Component inherits.

That way you can use [name-of-the-attribute] (namely, the CSS attribute selector), such as:

@Component({
    selector: "[other-attr]",
    ...
})
export class OtherAttrComponent {

Se demo plunker here.

The usual way is the CSS type (AKA element or tag) selector:

@Component({
    selector: "some-tag",
    ...
})

And it matches a tag with name some-tag.

You can even have a component that matches both a tag or an attribute:

@Component({
    selector: "other-both,[other-both]",
    template: `this is other-both ({{ value }})`
})
export class OtherBothComponent {

Demo plunker contains examples of all three.

Is [attributeName="attributeValue"] supported?

Yes. But mind the quotes. In the current implementation, the selector [attributeName="attributeValue"] actually matches <sometag attributeName='"attributeValue"'>, so test around before committing to this approach.

acdcjunior
  • 132,397
  • 37
  • 331
  • 304
  • Note: since any CSS selector is valid, you could even use class selectors such as `selector: '.my-class-name',` which would match any elements with such class. – acdcjunior Jul 20 '16 at 04:27
  • Great. thanks. I didn't see any reference to being able to pull this off when going through the Angular 2 site. So glad this is possible. – TehOne Jul 20 '16 at 20:47
  • 3
    is `[attributeName="attributeValue"]` supported? – Brad Kent Nov 15 '16 at 17:27
  • @BradKent Yes. But mind the quotes. The selector `[attributeName="attributeValue"]` actually matches `` – acdcjunior Nov 15 '16 at 17:47
  • 2
    The linter that comes with Angular CLI complains about components as attributes. Is there a way to disable that rule on a per file basis? – Votemike Jan 25 '17 at 18:27
  • 2
    @Votemike I haven't found a way to disable the error but if you add an element selector, in addition to the attribute selector, the error goes away. e.g., `selector: "my-selector,[my-selector]"` – mfink Jun 14 '18 at 19:43
13

Selector property of @Component decorator support, element selector, attribute selector and class selector:

1. Element selector:

@Component({
 selector: 'app-servers'
})

Usage: <app-servers></app-servers>

2. Attribute selector:

@Component({
 selector: '[app-servers]'
})

Usage: <div app-servers></div>

3. Class selector:

@Component({
 selector: '.app-servers'
})

Usage: <div class="app-servers"></div>

Note: Angular 2 does not support id and pseudo selectors

JulienD
  • 7,102
  • 9
  • 50
  • 84
Ankit Chaurasia
  • 785
  • 7
  • 7
10

Yes, according to this https://angular.io/docs/ts/latest/guide/cheatsheet.html (Components and Directives are very similar in general). Instead of using element selector:

selector: 'custom-element-name'

Use:

selector: '[custom-attribute-name]'

And in your parent component's template:

<div custom-attribute-name></div>
Harry Ninh
  • 16,288
  • 5
  • 60
  • 54
7

Absolutely. Essentially this is just a CSS selector, so if you need to use attribute you just do this:

@Component({
    selector: "my-tag[with-my-attribute]"
})
Alexander Leonov
  • 4,694
  • 1
  • 17
  • 25