SkillAgentSearch skills...

SwiftCodestyle

Style guide for writing in Swift.

Install / Use

/learn @surfstudio/SwiftCodestyle

README

Surf Swift Style Guide

Цели

Этот стайлгайд создан с целью:

  • Облегчить чтение и понимание незнакомого кода
  • Облегчить поддержку кода
  • Уменьшить вероятность совершения простых ошибок кодинга
  • Снизить когнитивную нагрузку при кодинге
  • Сфокусировать обсуждения в Pull Request-ах на логике, а не на стиле

Краткость кода не является основной целью. Код должен быть кратким только в том случае, если другие важные качества кода (такие как читаемость, простота и ясность) остаются равными или улучшаются.

Принципы

  • Этот гайд являеся дополнением официальному Swift API Design Guidelines
  • Мы стараемся сделать каждое правило проверяемым при помощи различных linter-ов

Содержание

Xcode форматирование

Вы можете добавить эти настройки воспользовавшись этим скриптом, как вариант, его вызов можно добавить в "Run Script" build phase.

  • <a id='column-width'></a><a href='#column-width'>#</a> Каждая строка должна иметь максимальную длину в 120 символов. SwiftLint: line_length

  • <a id='spaces-over-tabs'></a><a href='#spaces-over-tabs'>#</a> Используйте 4 пробела для отступов.

  • <a id='trailing-whitespace'></a><a href='#trailing-whitespace'>#</a> Строки не должны содержать пробелы в конце. SwiftFormat: trailingSpace SwiftLint: trailing_whitespace

Именование

  • <a id='use-camel-case'></a><a href='#use-camel-case'>#</a> Используйте PascalCase для названий типов и протоколов, и lowerCamelCase для всего остального. SwiftLint: type_name

    <details>
    protocol SpaceThing {
      // ...
    }
    
    class SpaceFleet: SpaceThing {
    
      enum Formation {
        // ...
      }
    
      class Spaceship {
        // ...
      }
    
      var ships: [Spaceship] = []
      static let worldName = "Earth"
    
      func addShip(_ ship: Spaceship) {
        // ...
      }
    }
    
    let myFleet = SpaceFleet()
    
    </details>

    Исключение: Вы можете поставить префикс подчеркивания перед приватным свойством если оно повторяет свойство или метод с одинаковым именем с более высоким уровнем доступа

    <details>

    Почему?

    Есть некоторые случаи при которых повторение названия свойства или метода может быть проще для чтения и понимания, чем использование другого имени.

    Например:

    final class BiometricAuthenticator {
    
      static var canAuthenticate: Bool {
          return _canAuthenticate()
      }
    
      ...
    
      private static func _canAuthenticate() {
        ...
      }
    
    }
    
    </details>
  • <a id='bool-names'></a><a href='#bool-names'>#</a> Называйте булевые переменные в формате isSpaceship, hasSpacesuit, и т.п. Так становится понятнее, что это именно Bool тип данных, а не какой-либо другой.

  • <a id='capitalize-acronyms'></a><a href='#capitalize-acronyms'>#</a> Акронимы в названиях (например URL) должны быть в верхнем регистре за исключением случаев, когда это начало названия которое должно быть в lowerCamelCase

    <details>
    // Неправильно
    class UrlValidator {
    
      func isValidUrl(_ URL: URL) -> Bool {
        // ...
      }
    
      func isUrlReachable(_ URL: URL) -> Bool {
        // ...
      }
    }
    
    let URLValidator = UrlValidator().isValidUrl(/* some URL */)
    
    // Правильно
    class URLValidator {
    
      func isValidURL(_ url: URL) -> Bool {
        // ...
      }
    
      func isURLReachable(_ url: URL) -> Bool {
        // ...
      }
    }
    
    let urlValidator = URLValidator().isValidURL(/* some URL */)
    
    </details>
  • <a id='general-part-first'></a><a href='#general-part-first'>#</a> Общая часть названия должна быть впереди, а более специфичная часть должна следовать за ней. Значение "общая часть" зависит от конеткста, но должно примерно означать "то, что больше всего помогает вам сузить поиск нужного элемента." Самое главное, будьте последовательны с тем, как вы располагаете части имен.

    <details>
    // Неправильно
    let rightTitleMargin: CGFloat
    let leftTitleMargin: CGFloat
    let bodyRightMargin: CGFloat
    let bodyLeftMargin: CGFloat
    
    // Правильно
    let titleMarginRight: CGFloat
    let titleMarginLeft: CGFloat
    let bodyMarginRight: CGFloat
    let bodyMarginLeft: CGFloat
    
    </details>
  • <a id='hint-at-types'></a><a href='#hint-at-types'>#</a> Включите подсказку о типе в имя, если в противном случае оно будет неоднозначным.

    <details>
    // Неправильно
    let title: String
    let cancel: UIButton
    
    // Правильно
    let titleText: String
    let cancelButton: UIButton
    
    </details>
  • <a id='past-tense-events'></a><a href='#past-tense-events'>#</a> Обработчики событий должны быть названы как предложения в настоящем времени. Детали можно опустить, если они не нужны для ясности.

    <details>
    // Неправильно
    class SomeViewController {
    
      private func didTapLogin() {
        // ...
      }
    
      private func didTapBookButton() {
        // ...
      }
    
      private func modelDidChange() {
        // ...
      }
    }
    
    // Правильно
    class SomeViewController {
    
      private func login() {
        // ...
      }
    
      private func handleBookButtonTap() {
        // ...
      }
    
      private func modelChanged() {
        // ...
      }
    }
    
    </details>
  • <a id='able-suffix-misuse'></a><a href='#able-suffix-misuse'>#</a> Названия протоколов должны явно отражать функциональное значение протоколов. Если протокол описывает методы, реализующие действия самого объекта над другими объектами, лучше использовать Noun; если же он описывает действия, которые можно совершить над объектом, реализующим протокол, лучше использовать Adjective с суффиксом -able.

    <details>
    // Неправильно
    protocol Presenter {
        func presentInView(view: UIView)
    }
    
    protocol AlertPresentable {
      func presentAlert(alert: Alert)
    }
    
    // Правильно
    protocol Presentable {
        func presentInView(view: UIView)
    }
    
    protocol AlertPresenter {
      func presentAlert(alert: Alert)
    }
    
    </details>

Стиль

  • <a id='use-implicit-types'></a><a href='#use-implicit-types'>#</a> Не указываете типы там, где они легко могут быть выведены

    <details>
    // Неправильно
    let host: Host = Host()
    
    // Правильно
    let host = Host()
    
    enum Direction {
      case left
      case right
    }
    
    func someDirection() -> Direction {
      // Неправильно
      return Direction.left
    
      // Правильно
      return .left
    }
    
    </details>
  • <a id='use-implicit-types'></a><a href='#use-implicit-types'>#</a> Условные операторы должны всегда вызывать return в следующей строке SwiftLint: conditional_returns_on_newline

    <details>
    // Неправильно
    guard true else { return }
    
    if true { return }
    
    // Правильно
    guard true else {
      return
    }
    
    if true {
      return
    }
    
    </details>
  • <a id='omit-self'></a><a href='#omit-self'>#</a> Не используйте self пока это не нужно для уточнения или пока того не требует язык. Это правило не касается инициализаторов, там нужно использовать self всегда. SwiftFormat: redundantSelf

    <details>
    final class Listing {
    
      init(capacity: Int, allowsPets: Bool) {
        // Правильно
        self.capacity = capacity
        self.isFamilyFriendly = !allowsPets
      }
    
      private let isFamilyFriendly: Bool
      private var capacity: Int
    
      private func increaseCapacity(by amount: Int) {
        // Неправильно
        self.capacity += amount
        self.save()
    
        // Правильно
        capacity += amount
        save()
      }
    }
    
    </details>
  • <a id='trailing-comma-array'></a><a href='#trailing-comma-array'>#</a> Следует избегать закрывающей запятой в массивах и словарях SwiftLint: trailing_comma

    <details>
    // Неправильно
    let rowContent = [
      listingUrgencyDatesRowContent(),
      listingUrgencyBookedRowContent(),
      listingUrgencyBookedShortRowContent(),
    ]
    
    // Правильно
    let rowContent = [
      listingUrgencyDatesRo
    

Related Skills

View on GitHub
GitHub Stars24
CategoryContent
Updated5mo ago
Forks10

Languages

Shell

Security Score

92/100

Audited on Nov 10, 2025

No findings