Каковы лучшие практики написания чистого и поддерживаемого кода?ruby-55

Чистый код — это не роскошь, а необходимость для профессиональной разработки. Вот проверенные практики, которые я собирал годами проведения code review и собеседований.

1. Следование принципам SOLID

Single Responsibility Principle

# Плохо
class UserManager
  def initialize(user)
    @user = user
  end

  def save_to_db
    # ...
  end

  def send_welcome_email
    # ...
  end
end

# Хорошо
class UserPersister
  def initialize(user)
    @user = user
  end

  def save
    # ...
  end
end

class UserNotifier
  def initialize(user)
    @user = user
  end

  def send_welcome_email
    # ...
  end
end

2. Соблюдение соглашений Ruby style guide

  • Именование: snake_case для методов, CamelCase для классов
  • Отступы: 2 пробела
  • Предпочитать &&/|| над and/or для логических операций

3. Эффективное использование модулей

module Loggable
  def log(message)
    puts "[#{self.class}] #{message}"
  end
end

class Order
  include Loggable

  def process
    log "Processing started"
    # ...
  end
end

4. Правильное использование методов-предикатов

# Хороший стиль
def active?
  @status == 'active'
end

# Использование
if user.active?
  # ...
end

5. Иммутабельность там, где возможно

# Лучше возвращать новый объект
class Calculator
  def add(a, b)
    a + b
  end
end

# Чем изменять состояние
class Calculator
  def initialize
    @result = 0
  end

  def add(n)
    @result += n
  end
end

6. Грамотная обработка ошибок

# Хорошая практика
def fetch_data
  raise ArgumentError, "URL cannot be blank" if url.empty?
  # ...
rescue Net::HTTPError => e
  logger.error "HTTP error: #{e.message}"
  retry if can_retry?
end

7. Документирование через тесты

describe OrderProcessor do
  it 'marks order as completed after successful payment' do
    order = create(:order)
    processor = OrderProcessor.new(order)

    expect { processor.process }.to change(order, :status).to('completed')
  end
end

8. Применение паттернов проектирования

Фабричный метод:

class ReportGenerator
  def self.for(type)
    case type
    when :csv then CsvReport.new
    when :pdf then PdfReport.new
    else raise "Unknown report type"
    end
  end
end

9. Рефакторинг "дурно пахнущего" кода

Признаки проблемного кода:

  • Методы длиннее 10 строк
  • Классы с более чем 100 строками
  • Глубокие цепочки вызовов (user.company.address.street)
  • Много условий в одном методе

10. Инструменты поддержания качества кода

  • RuboCop для статического анализа
  • Reek для обнаружения "code smells"
  • SimpleCov для контроля покрытия тестами
  • Pronto для автоматических проверок в CI

11. Эффективное использование блоков

# Хороший пример
File.open('file.txt') do |file|
  process_file(file)
end

# Лучше чем
file = File.open('file.txt')
process_file(file)
file.close

12. Правильная работа с коллекциями

# Предпочитать
users.select(&:active?).map(&:name)

# Чем
active_users = []
users.each do |user|
  if user.active?
    active_users << user.name
  end
end

Резюмируем: Чистый Ruby-код — это сочетание соблюдения соглашений, применения принципов ООП, грамотного проектирования и использования инструментов контроля качества. Код должен быть не только рабочим, но и читаемым, тестируемым и легко изменяемым. Помните: код читается гораздо чаще, чем пишется, поэтому инвестируйте время в его качество.