Laravel 프레임워크 학습 노트의 코드 개발 규범
단일 책임 원칙
하나의 종류와 방법은 하나의 직책만 책임진다.
잘못된 코드:
public function getFullNameAttribute()
{
if (auth()->user() && auth()->user()->hasRole('client') && auth()->user()->isVerified()) {
return 'Mr. ' . $this->first_name . ' ' . $this->middle_name . ' ' $this->last_name;
} else {
return $this->first_name[0] . '. ' . $this->last_name;
}
}
좋은 코드:
public function getFullNameAttribute()
{
return $this->isVerifiedClient() ? $this->getFullNameLong() : $this->getFullNameShort();
}
public function isVerfiedClient()
{
return auth()->user() && auth()->user()->hasRole('client') && auth()->user()->isVerified();
}
public function getFullNameLong()
{
return 'Mr. ' . $this->first_name . ' ' . $this->middle_name . ' ' . $this->last_name;
}
public function getFullNameShort()
{
return $this->first_name[0] . '. ' . $this->last_name;
}
뚱뚱 모형, 마른 컨트롤러
쿼리 구축기나 원본 SQL 쿼리를 사용한다면 모든 DB 관련 논리를 Eloquent 모델이나 Repository 클래스에 저장합니다.
잘못된 코드:
public function index()
{
$clients = Client::verified()
->with(['orders' => function ($q) {
$q->where('created_at', '>', Carbon::today()->subWeek());
}])
->get();
return view('index', ['clients' => $clients]);
}
좋은 코드:
public function index()
{
return view('index', ['clients' => $this->client->getWithNewOrders()]);
}
Class Client extends Model
{
public function getWithNewOrders()
{
return $this->verified()
->with(['orders' => function ($q) {
$q->where('created_at', '>', Carbon::today()->subWeek());
}])
->get();
}
}
확인
인증 논리를 컨트롤러에서 요청 클래스로 옮깁니다.
잘못된 코드:
public function store(Request $request)
{
$request->validate([
'title' => 'required|unique:posts|max:255',
'body' => 'required',
'publish_at' => 'nullable|date',
]);
....
}
좋은 코드:
public function store(PostRequest $request)
{
....
}
class PostRequest extends Request
{
public function rules()
{
return [
'title' => 'required|unique:posts|max:255',
'body' => 'required',
'publish_at' => 'nullable|date',
];
}
}
업무 논리는 서비스 클래스에 넣어야 한다
하나의 컨트롤러는 하나의 직책만 책임지기 때문에 업무 논리를 서비스 클래스로 옮겨야 한다.
잘못된 코드:
public function store(Request $request)
{
if ($request->hasFile('image')) {
$request->file('image')->move(public_path('images') . 'temp');
}
....
}
좋은 코드:
public function store(Request $request)
{
$this->articleService->handleUploadedImage($request->file('image'));
....
}
class ArticleService
{
public function handleUploadedImage($image)
{
if (!is_null($image)) {
$image->move(public_path('images') . 'temp');
}
}
}
DRY
가능한 한 코드를 복용하십시오. 단일 직책 원칙은 중복을 피하는 데 도움을 줄 수 있습니다. 또한, 가능한 한 Blade 템플릿을 복용하고, Eloquent 역할 영역을 사용하십시오.
잘못된 코드:
public function getActive()
{
return $this->where('verified', 1)->whereNotNull('deleted_at')->get();
}
public function getArticles()
{
return $this->whereHas('user', function ($q) {
$q->where('verified', 1)->whereNotNull('deleted_at');
})->get();
}
좋은 코드:
public function scopeActive($q)
{
return $q->where('verified', 1)->whereNotNull('deleted_at');
}
public function getActive()
{
return $this->active()->get();
}
public function getArticles()
{
return $this->whereHas('user', function ($q) {
$q->active();
})->get();
}
Eloquent 및 컬렉션 우선 사용
Eloquent를 통해 읽기 쉽고 유지보수성이 좋은 코드를 작성할 수 있으며, 또한 Eloquent는 소프트 삭제, 이벤트, 역할 영역 등 강력한 내장 도구를 제공한다.
잘못된 코드:
SELECT *
FROM `articles`
WHERE EXISTS (SELECT *
FROM `users`
WHERE `articles`.`user_id` = `users`.`id`
AND EXISTS (SELECT *
FROM `profiles`
WHERE `profiles`.`user_id` = `users`.`id`)
AND `users`.`deleted_at` IS NULL)
AND `verified` = '1'
AND `active` = '1'
ORDER BY `created_at` DESC
좋은 코드:
Article::has('user.profile')->verified()->latest()->get();
대량 할당
대량 할당에 대한 자세한 내용은 해당 문서를 볼 수 있습니다.
잘못된 코드:
$article = new Article;
$article->title = $request->title;
$article->content = $request->content;
$article->verified = $request->verified;
// Add category to article
$article->category_id = $category->id;
$article->save();
좋은 코드:
$category->article()->create($request->all());
Blade에서 쿼리 수행 및 로딩 필요 없음
잘못된 코드:
@foreach (User::all() as $user)
{{ $user->profile->name }}
@endforeach
좋은 코드:
$users = User::with('profile')->get();
...
@foreach ($users as $user)
{{ $user->profile->name }}
@endforeach
당신의 코드에 주석을 달다
잘못된 코드:
if (count((array) $builder->getQuery()->joins) > 0)
좋은 코드:
// Determine if there are any joins.
if (count((array) $builder->getQuery()->joins) > 0)
최적:
if ($this->hasJoins())
프런트엔드 코드와 PHP 코드를 분리하려면 다음과 같이 하십시오.
JS와 CSS 코드를 Blade 템플릿에 쓰지 마십시오. PHP 클래스에서 HTML 코드를 작성하지 마십시오.
잘못된 코드:
let article = `{{ json_encode($article) }}`;
좋은 코드:
JavaScript 파일에서 다음을 수행합니다.
let article = $('#article').val();
하드 인코딩 대신 구성, 언어 파일 및 상수 사용
잘못된 코드:
public function isNormal()
{
return $article->type === 'normal';
}
return back()->with('message', 'Your article has been added!');
좋은 코드:
public function isNormal()
{
return $article->type === Article::TYPE_NORMAL;
}
return back()->with('message', __('app.article_added'));
커뮤니티에 승인된 표준 Laravel 도구 사용
Laravel 내장 기능과 커뮤니티 버전 확장 패키지를 우선적으로 사용하고 그 다음은 제3자 확장 패키지와 도구입니다.이렇게 하면 이후의 학습과 유지 보수 비용을 낮추는 것이 장점이다.
과업
표준 도구
타사 도구
권한을 부여하다
정책 클래스
Entrust, Sentinel 등
자원 컴파일
Laravel Mix
Grunt, Gulp 등
개발 환경
Homestead
Docker
배치하다
Laravel Forge
Deployer 등
단원 테스트
PHPUnit、Mockery
Phpspec
브라우저 테스트
Laravel Dusk
Codeception
DB
Eloquent
SQL、Doctrine
거푸집
Blade
Twig
처리 데이터
Laravel 컬렉션
배열
양식 유효성 검사
요청 클래스
타사 확장 팩, 디렉터에서의 검증
인증
기능 내장
제3자 확장 패키지, 당신의 해결 방안
API 인증
Laravel Passport
타사 JWT 및 OAuth 확장 팩
API 생성
기능 내장
Dingo API 및 유사 확장 팩
DB 패브릭 작업
옮기다
DB 직접 조작
현지화
기능 내장
타사 도구
실시간 사용자 인터페이스
Laravel Echo、Pusher
타사가 WebSocket의 확장 팩을 직접 처리
테스트 데이터 생성
채우기 클래스, 모델 팩토리, 페이커
테스트 데이터 수동 생성
임무 스케줄링
Laravel Task Scheduler
스크립트 또는 타사 확장 팩
DB
MySQL、PostgreSQL、SQLite、SQL Server
MongoDB
Laravel 명명 규칙 준수
PSR 표준을 따릅니다.또한 Laravel 커뮤니티 버전의 이름 지정 규칙도 따릅니다.
What
How
Good
Bad
컨트롤러
홀수
ArticleController
ArticlesController
경로
복수
articles/1
article/1
라우팅 이름 지정
밑줄 +.번호 구분
users.show_active
users.show-active,show-active-users
모델
홀수
User
Users
일대일 연관
홀수
articleComment
articleComments,article_comment
기타 연관 관계
복수
articleComments
articleComment,article_comments
데이터 테이블
복수
article_comments
article_comment,articleComments
중간표
알파벳순으로 정렬된 단수 형식
article_user
user_article,article_users
테이블 필드
모델 이름 없이 밑줄
meta_title
MetaTitle; article_meta_title
외부 키
단수, 테이프접미사 id
article_id
ArticleId, id_article, articles_id
메인 키
-
id
custom_id
옮기다
-
2017_01_01_000000_create_articles_table
2017_01_01_000000_articles
메서드
낙타봉
getAll
get_all
자원 클래스 방법
문서
store
saveArticle
테스트 클래스 방법
낙타봉
testGuestCannotSeeArticle
test_guest_cannot_see_article
변량
낙타봉
$articlesWithAuthor
$articles_with_author
컬렉션
복수
$activeUsers = User::active()->get()
data
대상
홀수
$activeUser = User::active()->first()
obj
구성 및 언어 파일 인덱스
밑줄
articles_enabled
ArticlesEnabled; articles-enabled
뷰
밑줄
show_filtered.blade.php
showFiltered.blade.php, show-filtered.blade.php
프로비저닝
밑줄
google_calendar.php
googleCalendar.php, google-calendar.php
계약(인터페이스)
명사
Authenticatable
AuthenticationInterface, IAuthentication
Trait
형용사
Notifiable
NotificationTrait
줄임말이나 읽을 수 있는 문법을 사용하다
잘못된 코드:
$request->session()->get('cart');
$request->input('name');
좋은 코드:
session('cart');
$request->name;
추가 예:
통용 문법
가독성 향상
Session::get('cart')
session('cart')
$request->session()->get('cart')
session('cart')
Session::put('cart', $data)
session(['cart' => $data])
$request->input('name'), Request::get('name')
$request->name, request('name')
return Redirect::back()
return back()
is_null($object->relation) ? $object->relation->id : null }
optional($object->relation)->id
return view('index')->with('title', $title)->with('client', $client)
return view('index', compact('title', 'client'))
$request->has('value') ? $request->value : 'default';
$request->get('value', 'default')
Carbon::now(), Carbon::today()
now(), today()
App::make('Class')
app('Class')
->where('column', '=', 1)
->where('column', 1)
->orderBy('created_at', 'desc')
->latest()
->orderBy('age', 'desc')
->latest('age')
->orderBy('created_at', 'asc')
->oldest()
->select('id', 'name')->get()
->get(['id', 'name'])
->first()->name
->value('name')
IoC 컨테이너 또는 도어 사용
스스로 새로운 클래스를 만들면 코드의 결합도가 높고 테스트하기 어려울 것입니다. 대신 IoC 용기나 문면을 사용할 수 있습니다.
잘못된 코드:
$user = new User;
$user->create($request->all());
좋은 코드:
public function __construct(User $user)
{
$this->user = $user;
}
....
$this->user->create($request->all());
직접 따르지 마라.env 데이터 가져오기
코드 예
.env
파일의 설정:CDN_DOMAIN=cdndomain.com
config/app.php
파일의 설정:'cdn_domain' => env('CDN_DOMAIN', null),
프로그램에서 다음 두 가지 방법
을 가져옵니다.env('CDN_DOMAIN')
config('app.cdn_domain')
여기에 모든 프로그램 설정 정보는
config()
를 통해 읽어야 하고 모든 .env
설정 정보는 config()
를 통해 읽어야 하며 설정 파일 이외의 범위에서 사용하지 않아야 한다env()
.프로필에 데이터를 전달하고
config
보조 함수로 데이터를 얻습니다.잘못된 코드:
$apiKey = env('API_KEY');
좋은 코드:
// config/api.php
'key' => env('API_KEY'),
// Use the data
$apiKey = config('api.key');
어떤 우세가 있는가
이렇게 하면 주로 다음과 같은 몇 가지 장점이 있다.
config()
는 설정 정보이며 env()
는 서로 다른 환경을 구분하는 데 사용된다.config
에 통일적으로 배치하면 프레임워크의 설정 정보 캐시 기능을 이용하여 운행 효율을 높일 수 있다.config()
은 env()
위에 추상층을 하나 더 내면 코드를 더욱 건장하고 유연하게 할 수 있다.날짜를 표준 형식으로 저장하다
액세스 및 수정자를 사용하여 날짜 형식을 편집합니다.
잘못된 코드:
{{ Carbon::createFromFormat('Y-d-m H-i', $object->ordered_at)->toDateString() }}
{{ Carbon::createFromFormat('Y-d-m H-i', $object->ordered_at)->format('m-d') }}
좋은 코드:
// Model
protected $dates = ['ordered_at', 'created_at', 'updated_at']
public function getMonthDayAttribute($date)
{
return $date->format('m-d');
}
// View
{{ $object->ordered_at->toDateString() }}
{{ $object->ordered_at->monthDay }}
다른 좋은 실천
어떤 업무 논리도 루트 파일에 쓰지 마세요.
Blade 템플릿에서는 기본 PHP를 사용하지 않는 것이 좋습니다.
이 내용에 흥미가 있습니까?
현재 기사가 여러분의 문제를 해결하지 못하는 경우 AI 엔진은 머신러닝 분석(스마트 모델이 방금 만들어져 부정확한 경우가 있을 수 있음)을 통해 가장 유사한 기사를 추천합니다:
다양한 언어의 JSONJSON은 Javascript 표기법을 사용하여 데이터 구조를 레이아웃하는 데이터 형식입니다. 그러나 Javascript가 코드에서 이러한 구조를 나타낼 수 있는 유일한 언어는 아닙니다. 저는 일반적으로 '객체'{}...
텍스트를 자유롭게 공유하거나 복사할 수 있습니다.하지만 이 문서의 URL은 참조 URL로 남겨 두십시오.
CC BY-SA 2.5, CC BY-SA 3.0 및 CC BY-SA 4.0에 따라 라이센스가 부여됩니다.