Difference between revisions of "Front-End Standard"
Line 73: | Line 73: | ||
* “x” = Not Applicable. | * “x” = Not Applicable. | ||
+ | |||
+ | {| class="wikitable" border="1" | ||
+ | |- | ||
+ | ! Identifier | ||
+ | ! Public | ||
+ | ! Protected | ||
+ | ! Internal | ||
+ | ! Private | ||
+ | ! Notes | ||
+ | |- | ||
+ | | Project File | ||
+ | | P | ||
+ | | x | ||
+ | | x | ||
+ | | x | ||
+ | | Match Assembly & Namespace. | ||
+ | |- | ||
+ | | Source File | ||
+ | | P | ||
+ | | x | ||
+ | | x | ||
+ | | x | ||
+ | | Match contained class. | ||
+ | |- | ||
+ | | Other Files | ||
+ | | P | ||
+ | | x | ||
+ | | x | ||
+ | | x | ||
+ | | Apply where possible. | ||
+ | |- | ||
+ | | Namespace | ||
+ | | P | ||
+ | | x | ||
+ | | x | ||
+ | | x | ||
+ | | Partial Project/Assembly match. | ||
+ | |- | ||
+ | | Class or Struct | ||
+ | | P | ||
+ | | P | ||
+ | | P | ||
+ | | P | ||
+ | | Add suffix of subclass. | ||
+ | |- | ||
+ | | Interface | ||
+ | | P | ||
+ | | P | ||
+ | | P | ||
+ | | P | ||
+ | | Prefix with a capital I. | ||
+ | |- | ||
+ | | Source FileGeneric Class | ||
+ | | P | ||
+ | | P | ||
+ | | P | ||
+ | | P | ||
+ | | Use T or K as Type identifier. | ||
+ | |- | ||
+ | | Method | ||
+ | | P | ||
+ | | P | ||
+ | | P | ||
+ | | P | ||
+ | | Use a Verb or Verb-Object pair | ||
+ | |- | ||
+ | | Property | ||
+ | | P | ||
+ | | P | ||
+ | | P | ||
+ | | P | ||
+ | | Do not prefix with Get or Set. | ||
+ | |- | ||
+ | | Field | ||
+ | | P | ||
+ | | P | ||
+ | | v | ||
+ | | _c | ||
+ | | Only use Private fields.No Hungarian Notation! | ||
+ | |- | ||
+ | | Constant | ||
+ | | P | ||
+ | | P | ||
+ | | P | ||
+ | | _c | ||
+ | | | ||
+ | |- | ||
+ | | Static Field | ||
+ | | P | ||
+ | | P | ||
+ | | P | ||
+ | | _c | ||
+ | | Only use Private fields. | ||
+ | |- | ||
+ | | Enum | ||
+ | | P | ||
+ | | P | ||
+ | | P | ||
+ | | P | ||
+ | | Options are also Pascal Case. | ||
+ | |- | ||
+ | | Delegate | ||
+ | | P | ||
+ | | P | ||
+ | | P | ||
+ | | P | ||
+ | | | ||
+ | |- | ||
+ | | Event | ||
+ | | P | ||
+ | | x | ||
+ | | x | ||
+ | | x | ||
+ | | | ||
+ | |- | ||
+ | | Inline Variable | ||
+ | | x | ||
+ | | x | ||
+ | | x | ||
+ | | c | ||
+ | | Avoid single-character and enumerated names. | ||
+ | |- | ||
+ | | Parameter | ||
+ | | P | ||
+ | | x | ||
+ | | x | ||
+ | | c | ||
+ | | | ||
+ | |} | ||
+ | |||
+ | ==Coding Style== | ||
+ | |||
+ | {| class="wikitable" border="1" | ||
+ | |- | ||
+ | ! Code | ||
+ | ! Style | ||
+ | |- | ||
+ | | Source Files | ||
+ | | One Namespace per file and one class per file. | ||
+ | |- | ||
+ | | Curly Braces | ||
+ | | On new line. Always use braces when optional. | ||
+ | |- | ||
+ | | Indention | ||
+ | | Use tabs with size of 4. | ||
+ | |- | ||
+ | | Comments | ||
+ | | Use // or /// but not /* … */ and do not flowerbox. | ||
+ | |- | ||
+ | | Variables | ||
+ | | One variable per declaration. | ||
+ | |} | ||
+ | |||
+ | ==Language Usage== | ||
+ | |||
+ | {| class="wikitable" border="1" | ||
+ | |- | ||
+ | ! Code | ||
+ | ! Style | ||
+ | |- | ||
+ | | Native Data Types | ||
+ | | Use built-in C# native data types vs .NET CTS types. (Use int NOT Int32) | ||
+ | |- | ||
+ | | Enums | ||
+ | | Avoid changing default type. | ||
+ | |- | ||
+ | | Generics | ||
+ | | Prefer Generic Types over standard or strong-typed classes. | ||
+ | |- | ||
+ | | Properties | ||
+ | | Never prefix with Get or Set. | ||
+ | |- | ||
+ | | Methods | ||
+ | | Use a maximum of 7 parameters. | ||
+ | |- | ||
+ | | base and this | ||
+ | | Use only in constructors or within an override. | ||
+ | |- | ||
+ | | Ternary conditions | ||
+ | | Avoid complex conditions. | ||
+ | |- | ||
+ | | for each statements | ||
+ | | Do not modify enumerated items within a foreach statement. | ||
+ | |- | ||
+ | | Conditionals | ||
+ | | Avoid evaluating Boolean conditions against true or false.No embedded assignment.Avoid embedded method invocation. | ||
+ | |- | ||
+ | | Exceptions | ||
+ | | Do not use exceptions for flow control.Use throw; not throw e; when re-throwing.Only catch what you can handle.Use validation to avoid exceptions.Derive from Execption not ApplicationException. | ||
+ | |- | ||
+ | | Events | ||
+ | | Always check for null before invoking. | ||
+ | |- | ||
+ | | Locking | ||
+ | | Use lock() not Monitor.Enter().Do not lock on an object type or “this”.Do lock on private objects. | ||
+ | |- | ||
+ | | Dispose() & Close() | ||
+ | | Always invoke them if offered, declare where needed. | ||
+ | |- | ||
+ | | Finalizers | ||
+ | | Avoid.Use the C# Destructors.Do not create Finalize() method. | ||
+ | |- | ||
+ | | Assembly Version | ||
+ | | Increment manually. | ||
+ | |- | ||
+ | | ComVisibleAttribute | ||
+ | | Set to false for all assemblies | ||
+ | |} | ||
+ | |||
+ | ==Naming Conventions== | ||
+ | |||
+ | Consistency is the key to maintainable code. This statement is most true for naming your projects, source files, and identifiers including Fields, Variables, Properties, Methods, Parameters, Classes, Interfaces, and Namespaces. | ||
+ | |||
+ | ==General Guidelines== | ||
+ | |||
+ | *Always use Camel Case or Pascal Case names. | ||
+ | *Avoid ALL CAPS and all lowercase names. Single lowercase words or letters are acceptable. | ||
+ | *Do not create declarations of the same type (namespace, class, method, property, field, or parameter) and access modifier (protected, public, private, internal) that vary only by capitalization. | ||
+ | *Do not use names that begin with a numeric character. | ||
+ | *Do add numeric suffixes to identifier names. | ||
+ | *Always choose meaningful and specific names. | ||
+ | *Variables and Properties should describe an entity not the type or size. | ||
+ | *Do not use Hungarian Notation! | ||
+ | |||
+ | Example: strName or iCount | ||
+ | |||
+ | *Avoid using abbreviations unless the full name is excessive. | ||
+ | *Avoid abbreviations longer than 5 characters. | ||
+ | *Any Abbreviations must be widely known and accepted. | ||
+ | *Use uppercase for two-letter abbreviations, and Pascal Case for longer abbreviations. | ||
+ | *Do not use C# reserved words as names. | ||
+ | *Avoid naming conflicts with existing .NET Framework namespaces, or types. | ||
+ | *Avoid adding redundant or meaningless prefixes and suffixes to identifiers | ||
+ | Example: | ||
+ | // Bad! | ||
+ | public enum ColorsEnum {…} | ||
+ | public class CVehicle {…} | ||
+ | public struct RectangleStruct {…} | ||
+ | *Do not include the parent class name within a property name. | ||
+ | |||
+ | Example: Customer.Name NOT Customer.CustomerName | ||
+ | *Try to prefix Boolean variables and properties with “Can”, “Is” or “Has”. | ||
+ | *Append computational qualifiers to variable names like Average, Count, Sum, Min, and Max where appropriate. | ||
+ | *When defining a root namespace, use a Product, Company, or Developer Name as the root. Example: SmartHCM.StringUtilities |
Revision as of 07:20, 30 April 2015
Contents
Introduction
This document describes rules and recommendations for developing applications in .NET and class libraries using the C# Language. The goal is to define guidelines to enforce consistent style and formatting and help developers avoid common pitfalls and mistakes.
This document covers Naming Conventions, Coding Style, Language Usage, Object Model Design and Tips for developers.
Document Convention
Much like the ensuing coding standards, this document requires standards in order to ensure clarity when stating the rules and guidelines. Certain conventions are used throughout this document to add emphasis.
Below are some of the common conventions used throughout this document.
Coloring & Emphasis
Blue: Text colored blue indicates a keyword or .NET type.
Bold: Text with additional emphasis to make it stand-out.
Keywords
Always: Emphasizes this rule must be enforced.
Never: Emphasizes this action must not happen.
Do Not: Emphasizes this action must not happen.
Avoid: Emphasizes that the action should be prevented, but some exceptions may exist.
Try: Emphasizes that the rule should be attempted whenever possible and appropriate.
Example:Precedes text used to illustrate a rule or recommendation.
Reason: Explains the thoughts and purpose behind a rule or recommendation.
Terminology & Definitions
The following terminology is referenced throughout this document:
Access Modifier
C# keywords public, protected, internal, and private declare the allowed code-accessibility of types and their members. Although default access modifiers vary, classes and most other members use the default of private. Notable exceptions are interfaces and enums which both default to public.
Camel Case
A word with the first letter lowercase, and the first letter of each subsequent word-part capitalized.
Example: customerName
Common Type System
The .NET Framework common type system (CTS) defines how types are declared, used, and managed. All native C# types are based upon the CTS to ensure support for cross-language integration.
Identifier
A developer defined token used to uniquely name a declared object or object instance.
Example: public class MyClassNameIdentifier { … }
Pascal Case
A word with the first letter capitalized, and the first letter of each subsequent word-part capitalized.
Example: CustomerName
Premature Generalization
As it applies to object model design; this is the act of creating abstractions within an object model not based upon concrete requirements or a known future need for the abstraction. In simplest terms: “Abstraction for the sake of Abstraction.”
Flags
The following flags are used to help clarify or categorize certain statements:
Quick Summary This section contains tables describing a high-level summary of the major standards covered in this document. These tables are not comprehensive, but give a quick glance at commonly referenced elements.
Naming Conventions
- “c” = camelCase
- “P” = PascalCase
- “_” = Prefix with _Underscore
- “x” = Not Applicable.
Identifier | Public | Protected | Internal | Private | Notes |
---|---|---|---|---|---|
Project File | P | x | x | x | Match Assembly & Namespace. |
Source File | P | x | x | x | Match contained class. |
Other Files | P | x | x | x | Apply where possible. |
Namespace | P | x | x | x | Partial Project/Assembly match. |
Class or Struct | P | P | P | P | Add suffix of subclass. |
Interface | P | P | P | P | Prefix with a capital I. |
Source FileGeneric Class | P | P | P | P | Use T or K as Type identifier. |
Method | P | P | P | P | Use a Verb or Verb-Object pair |
Property | P | P | P | P | Do not prefix with Get or Set. |
Field | P | P | v | _c | Only use Private fields.No Hungarian Notation! |
Constant | P | P | P | _c | |
Static Field | P | P | P | _c | Only use Private fields. |
Enum | P | P | P | P | Options are also Pascal Case. |
Delegate | P | P | P | P | |
Event | P | x | x | x | |
Inline Variable | x | x | x | c | Avoid single-character and enumerated names. |
Parameter | P | x | x | c |
Coding Style
Code | Style |
---|---|
Source Files | One Namespace per file and one class per file. |
Curly Braces | On new line. Always use braces when optional. |
Indention | Use tabs with size of 4. |
Comments | Use // or /// but not /* … */ and do not flowerbox. |
Variables | One variable per declaration. |
Language Usage
Code | Style |
---|---|
Native Data Types | Use built-in C# native data types vs .NET CTS types. (Use int NOT Int32) |
Enums | Avoid changing default type. |
Generics | Prefer Generic Types over standard or strong-typed classes. |
Properties | Never prefix with Get or Set. |
Methods | Use a maximum of 7 parameters. |
base and this | Use only in constructors or within an override. |
Ternary conditions | Avoid complex conditions. |
for each statements | Do not modify enumerated items within a foreach statement. |
Conditionals | Avoid evaluating Boolean conditions against true or false.No embedded assignment.Avoid embedded method invocation. |
Exceptions | Do not use exceptions for flow control.Use throw; not throw e; when re-throwing.Only catch what you can handle.Use validation to avoid exceptions.Derive from Execption not ApplicationException. |
Events | Always check for null before invoking. |
Locking | Use lock() not Monitor.Enter().Do not lock on an object type or “this”.Do lock on private objects. |
Dispose() & Close() | Always invoke them if offered, declare where needed. |
Finalizers | Avoid.Use the C# Destructors.Do not create Finalize() method. |
Assembly Version | Increment manually. |
ComVisibleAttribute | Set to false for all assemblies |
Naming Conventions
Consistency is the key to maintainable code. This statement is most true for naming your projects, source files, and identifiers including Fields, Variables, Properties, Methods, Parameters, Classes, Interfaces, and Namespaces.
General Guidelines
- Always use Camel Case or Pascal Case names.
- Avoid ALL CAPS and all lowercase names. Single lowercase words or letters are acceptable.
- Do not create declarations of the same type (namespace, class, method, property, field, or parameter) and access modifier (protected, public, private, internal) that vary only by capitalization.
- Do not use names that begin with a numeric character.
- Do add numeric suffixes to identifier names.
- Always choose meaningful and specific names.
- Variables and Properties should describe an entity not the type or size.
- Do not use Hungarian Notation!
Example: strName or iCount
- Avoid using abbreviations unless the full name is excessive.
- Avoid abbreviations longer than 5 characters.
- Any Abbreviations must be widely known and accepted.
- Use uppercase for two-letter abbreviations, and Pascal Case for longer abbreviations.
- Do not use C# reserved words as names.
- Avoid naming conflicts with existing .NET Framework namespaces, or types.
- Avoid adding redundant or meaningless prefixes and suffixes to identifiers
Example: // Bad! public enum ColorsEnum {…} public class CVehicle {…} public struct RectangleStruct {…}
- Do not include the parent class name within a property name.
Example: Customer.Name NOT Customer.CustomerName
- Try to prefix Boolean variables and properties with “Can”, “Is” or “Has”.
- Append computational qualifiers to variable names like Average, Count, Sum, Min, and Max where appropriate.
- When defining a root namespace, use a Product, Company, or Developer Name as the root. Example: SmartHCM.StringUtilities