Skip to content

Code conventions

Ecanus edited this page Jun 16, 2025 · 7 revisions

In this document are guidelines on how to create and maintain effective code, design, documentation and style within Plural.

The majority of these guidelines were taken from Effective Dart.

How to read the guides

  • DO guidelines describe practices that should always be followed.
  • PREFER guidelines are practices that you should follow. However, they may be circumstances where it make sense to do otherwise.
  • AVOID guidelines are the dual to "prefer", that is, things you shouldn't do, but where they may be good reason to on rare occasions.

Code

DO limit partial imports to five or less attributes

When five, or fewer, properties are used from a library, only import the properties that are needed. For example:

import 'package:flutter/material.dart' show InlineSpan, TextSpan;

AVOID catches without on clauses

A catch clause without an onqualifier catches anything thrown by the code in the try block. In most cases, you should have an on clause to facilitate the kinds of runtime failures that are correctly handled.

If a general catch must be implemented, be sure to log, display or rethrow the error.

DO use rethrow to rethrow a caught exception

If an exception needs to be rethrown, prefer using the rethrow statement rather than throwing the same exception using throw.

This is because rethrow preserves the original stack trace of the exception (while throw resets the stack trace to the last thrown position).


Design

PREFER putting the most descriptive noun last

When naming an property, the last word should be the most descriptive aspect of the property.

_timelineAsksList // A list of Asks that are displayed on the timeline.
creationDate // The date that the Ask was created.
timeRemainingString // A string describing the time remaining before an Ask's deadline date.

PREFER non-imperative verb phrases for boolean properties or variables

Good names tend to start with one of a few kinds of verbs:

  • a form of "to be": isMouseHovered, wasShown, willFire.
  • an auxiliary verb: hasElements _canQueryGardens, shouldConsume.
  • an active verb: showsCloseIcon,excludesCurrentGarden

A boolean name should not sound like a command, because accessing a property doesn't change the object.


Documentation

DO start doc comments with a single-sentence summary

Start your doc comment with a brief, user-centric description ending with a period. Provide just enough context for the reader to decide if they should keep reading or look elsewhere for a solution for their problem.

DO separate the first sentence of a doc comment into its own paragraph

Add a blank line after the first sentence to split it out to its own paragraph. If more than a single sentence of explanation is needed, put the rest in later paragraphs.

/// Sets the value of [_currentGarden] to null without notifying listeners.
///
/// Clears all database subscriptions as well.

PREFER starting a boolean variable or property comment with "Whether" followed by a noun or gerund phrase

The doc comment should clarify the states this variable represents.

/// Whether the modal is currently displayed to the user.
bool isVisible;

// Whether resizing the current browser window will resize the modal.
bool get canResize => ...

Style

Identifiers

DO name import prefixes using lowercase_with_underscores

import 'dart:math' as math;
import 'package:angular_components/angular_components.dart' as angular_components;

DO name other identifiers using lowerCamelCase

Class members, top-level definitions, variables, parameters, and named parameters should capitalise the first letter of each word except the first word, and use no separators.

var count = 3;

HttpRequest = httpRequest;

void align(bool clearItms) {
    // ...
}

PREFER using lowerCamelCase for constant names

Use lowerCamelCase for constant variables, including enum values.

const pi = 3.14;
const defaultTimeout = 1000;

DO capitalise acronyms and abbreviations longer than two letters like words

// Longer than two letters, so like a word:
Http // "hypertext transfer protocol"
Uri // "uniform resource identifier"

// Two letters, capitalised in English, so capitalised in an identifier
ID // "identifier"
UI // "user interface"

// Two letters, not capitalised in English, so like a word in identifier
Rd // "road"
St // "street" or "saint"

When any form of abbreviation comes at the beginning of a lowerCamelCase identifier, the abbreviation should be all lowercase:

var httpConnection = connect();
var tvSet = Television();
var mrRogers = "hello, world";

PREFER using wildcards for unused callback parameters

Sometimes the type signature of a callback function requires a parameter, but the callback implementation doesn't use that parameter. In this case, it's idiomatic to name the unused parameter _, which declares a wildcard variable that is non-binding.

futureOfVoid.then((_) {
    print('Operation complete.');
});

Ordering

DO place dart: imports before other imports

import 'dart:async';
import 'dart:collection';

import 'package:bar/bar.dart';
import 'package:foo/foo.dart';

DO place package: imports before relative imports

import 'package:bar/bar.dart';
import 'package:foo/foo.dart';

import 'util.dart';

DO sort sections alphabetically

// Auth
import 'package:plural_app/src/features/authentication/domain/app_user.dart';

// Common Functions
import 'package:plural_app/src/common_functions/markdown.dart';

// Constants
import 'package:plural_app/src/constants/app_values.dart';
import 'package:plural_app/src/constants/fields.dart';
import 'package:plural_app/src/constants/formats.dart';

// Utils
import 'package:plural_app/src/utils/app_state.dart';

Clone this wiki locally