Use Appropriate Naming Conventions

Severity: Low

Description

Inconsistent or unclear naming conventions can create confusion, making the codebase harder to read and maintain. Vague function, variable, or type names can slow down development and increase the likelihood of errors, as developers may struggle to understand the purpose of various components. Clear and consistent naming conventions improve code readability, reduce ambiguity, and help maintain an organized codebase that is easier to work with, especially as the project grows. By adhering to proper naming conventions, developers ensure that their code is intuitive, maintainable, and scalable.

What should be avoided

Vague or inconsistent naming conventions make it unclear what a function, variable, or type is supposed to do. Here are several examples of poor naming practices:

Functions

#![allow(unused)]
fn main() {
// Function name lacks specificity.
// Also, it does not follow the snake-case naming convention.
fn processData() {
    // ...
}

// Function name is too generic.
fn doStuff() {
    // ...
}
}

Variables

#![allow(unused)]
fn main() {
// Variable name 'x' does not convey its purpose.
let x = 10;

// 'tmp' is not descriptive of its role.
let tmp = calculate_total();
}

Types

#![allow(unused)]
fn main() {
// The type alias 'B' provides no clarity about its purpose.
type B = u32;

// Struct and field names lack descriptive context.
struct Info {
    count: u32,
    extra_data: Vec<u8>,
}
}

In these examples:

  • The function names processData and doStuff are too vague, providing no insight into their purpose.
  • The variable names x and tmp do not describe the data they hold, making the code harder to follow.
  • The type alias T and struct Info lack meaningful context, obscuring their intent.

Best practice

Use clear and descriptive names that convey the purpose and role of each function, variable, or type, and follow consistent naming styles:

Functions

#![allow(unused)]
fn main() {
// Descriptive function name specifies that it processes transaction data.
fn process_transaction_data() {
    // ...
}

// Descriptive name clearly conveys the function's purpose.
fn calculate_user_balance() {
    // ...
}
}

Variables

#![allow(unused)]
fn main() {
// Variable name 'total_price' indicates its role in the calculation.
let total_price = 10;

// Descriptive variable name reflects its purpose
let updated_balance = calculate_total();
}

Types

#![allow(unused)]
fn main() {
// Provides context that the alias represents a user's balance.
type AccountBalance = u32;

// Meaningful struct and field names improve clarity.
struct UserDetails {
    age: u32,
    email: Vec<u8>,
    balance: AccountBalance,
}
}

This approach helps improve readability and consistency across the codebase, making it easier for developers to understand and maintain the code.