Domanda

I am trying to write a StyleCop-rule which checks for maintainability conventions.

When targeting a Struct, I want to skip the Struct if it is declared with a StructLayoutAttribute.

As described in the following code, I target a Struct. If the Struct contains the StructLayoutAttribute, I want to return.

But how do I put the attribute inside the contain-method; because it is not included in the StyleCop API?

Edit: I have added new logic of what I have tried; with all the ways of trying down below, the fields inside a struct with the attribute still get flagged by StyleCop.

public void IsStructNameCorrect(Struct structItem)
{
    string attribText = "";

    if (structItem.Attributes.Count == 1)
        return;

    if(structItem.Attributes.Contains(/*StructLayoutAttributeHere*/)
        return;

    foreach (Attribute attrib in structItem.Attributes)
    {
        attribText = attribText + attrib.CodePartType;
    }

    if (attribText.Contains("Layout"))
        return;

    foreach (CsElement csElement in structItem.ChildElements)
    {
        if (csElement.ElementType == ElementType.Field)
        {
            Field field = (Field)csElement;
            if (!field.Readonly)
            {
                AddViolation(field, field.LineNumber, "FieldNotReadOnly", field.Name);
            }
        }

    }
}
È stato utile?

Soluzione

I managed to get there myself; though kind of in a dirty way, but it does the job. If anyone does know how to actually target the attribute please do tell!

What it did is I used a bool that sets to true if the struct-attributes contain the text "StructLayout".

Then below I check if the attribute is false, and if it is I add violations if the field is not readonly.

public void IsStructNameCorrect(Struct structItem)
{
    string attribText = "";
    bool hasStructLayout = false;

    foreach (Attribute attrib in structItem.Attributes)
        attribText = attribText + attrib.Text;

    if (attribText.Contains("StructLayout"))
        hasStructLayout = true;

    if (!hasStructLayout)
    {
        foreach (CsElement csElement in structItem.ChildElements)
        {
            if (csElement.ElementType == ElementType.Field)
            {
                Field field = (Field)csElement;
                if (!field.Readonly)
                {
                    AddViolation(field, field.LineNumber, "FieldNotReadOnly", field.Name);
                }
            }
        }
    }
}
Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top