Home
home
버블박스
home
🍠

페이지 로딩 속도 분석

햇갈리거나 잘 모르는 이론 및 개념이 있다면 아래에 남겨주세요.
버블 활용 질문은 가급적 모두의 노코드에 남겨주세요.

1. 군고구마 같은 로딩 속도, 왜 그럴까?

버블로 열심히 만든 서비스! 프리뷰 모드에서 테스트를 해보니 생각보다 속도가 너무 느려서 답답할 때가 있습니다. 이게 버블의 한계 때문인지 아니면 내가 뭘 잘못했는지 몰라서, 더 답답하게만 느껴집니다. 사실 빌드 최적화를 잘 모른다면, 후자의 이유인 경우가 더 많습니다. 왜냐면 저도 그랬거든
속도가 느린 경우의 대다수 원인은 아래와 같습니다.
원인
해결 방법
하드 노코딩(?)으로 만든 요소들
- 재사용 요소 사용하기 - 요소 스타일 사용하기 - 페이지가 실행될 때, 보여줘야 하는 요소인지 파악하기
호출이 느린 이미지
- webp로 변환한 이미지 사용 - ignore_imgix=true 사용하기
무지성 데이터 호출
- Do a search for 최적화하기 - 데이터베이스 구조 최적화하기
무거운 플러그인
- 불필요한 플러그인 삭제하기 - 플러그인 직접 개발하기

2. 하드 노코딩(?)으로 만든 요소들

버블을 잘 모르지만 무작정 빌드를 시작한 상남자라면 요소의 호출 최적화를 고려하지 못하는 경우가 많습니다. 저도 잘 모르지만 빌드하면서 배운다는 입장이지만, 적어도 해당 개념을 알고 시작하는 게 좋습니다. 페이지가 실행되면, 버블에서 페이지에 존재하는 요소들을 불러옵니다. 이때, 어떻게 요소를 설정했느냐에 따라 호출 속도도 달라집니다.
페이지 작업을 할 때, 아래 부분을 숙지하면 도움이 됩니다.
재사용 요소 사용하기
요소 스타일 사용하기
페이지가 실행될 때, 보여줘야 하는 요소인지 파악하기
재사용 요소 사용하기
재사용 요소란 한 번 만든 요소를 여러 페이지에서 반복적으로 사용할 수 있는 요소입니다. 페이지 네비게이션에서 [Reusable elements]가 존재합니다. 여기서 재사용 요소를 만들 수 있습니다. 이렇게 만든 요소는 모든 페이지에서 바로 사용할 수 있습니다. 예를 들어 헤더나 푸터 같이 여러 페이지에서 동일하게 사용하는 요소는 재사용 요소를 사용하는 게 호출을 더 빠르게 만듭니다.
스타일 사용하기
[스타일] 탭에서 각 요소 별로 디자인 스타일을 지정할 수 있습니다. 해당 스타일을 사용하면 호출 속도를 단축시킬 수 있습니다.
페이지가 실행될 때, 보여줘야 하는 요소인지 파악하기
일부 요소들은 특정 조건을 기준으로 출력을 결정합니다.예를 들어 유저가 특정 버튼을 클릭했을 때 버튼 위에 보여지는 문구나, 특정 조건을 만족한 유저에게만 보여지는 버튼이 있습니다. 이러한 유형의 요소들은 페이지가 실행될 때, 호출할 필요가 없습니다.
이런 요소들은 [layout] 탭에서 [This element is visible on page load]를 비활성화하고, [Collpase when hidden]을 활성화 합니다. 그러면 페이지가 로딩될 때, 해당 요소들은 호출 대상에서 제외됩니다. 참고로 [Collpase when hidden]을 활성화 해야 해당 요소가 보이지 않을 때, 빈 공간을 차지하지 않습니다.
그리고 [Conditional] 탭에서 특정 조건을 만족할 때, 요소가 보여주도록 설정하면 됩니다.

3. 호출이 느린 이미지

페이지에서 요소와 이미지, 각각이 출력되는 로직은 독립적입니다. 이미지 출력 로직은 다음과 같습니다.
1.
클라이언트에서 클라우드에 이미지 호출 요청
2.
클라우드가 클라이언트의 요청을 확인하고 응답
3.
응답 값을 활용해 클라이언트에서 이미지 출력
버블의 [데이터] > [file manager]로 이동하면, 현재 내 앱의 클라우드에 저장된 이미지를 확인할 수 있습니다. 여기서 이미지를 클릭해보면 해당 클라우드에서 저장된 이미지 경로를 확인할 수 있습니다.
https://9243ba6a72900736840bcabe631c20bc.cdn.bubble.io/f1714903771047x192240131934809500/CP00002070_20240119164433.jpg?_gl=1*1lxr29g*_gcl_aw*R0NMLjE3MTQ2NjE0NzEuQ2p3S0NBanc4OHl4QmhCV0Vpd0E3Y202cFhzY0lpTXQ2TnZfVUx3Zk50NXA5WDNfWmU2VW1Gbkp5Q2pQb005SE5jQWpRZXNDUlNjYVNob0NQZVlRQXZEX0J3RQ..*_gcl_au*MjEyODM1OTA5Ny4xNzA4ODU4ODQx*_ga*MTAzODU0MjQ5MS4xNzA4ODU4ODQx*_ga_BFPVR2DEE2*MTcxNDg0NjE0My40MC4xLjE3MTQ5MTkwMDguNjAuMC4w
Python
복사
이미지 호출 속도를 높일려면 아래 2가지를 사용하시면 됩니다.
ignore_imgix=true 사용하기
webpy로 변환한 이미지 사용
ignore_imgix=true 사용하기
클라우드의 이미지 경로 마지막아 파라미터로 “?ignore_imgix=true” 를 추가하면 속도가 눈에 띄게 개선이 된다고 합니다. 오른쪽이 ignore_imgix=true 파라미터를 추가했을 때의 로딩 속도라고 하네요.
이미지 요소의 [Dynamic image] 미지막에 아래처럼 파라미터를 추가하면 됩니다.
저도 이건 포럼에서 확인한 건데 사실 자세한 이론 공부는 안 했습니다. 왜냐면 영어가 넘 복잡하거든요 자세한 이론은 아래 링크에서 확인할 수 있으니, 테크 덕후면 한 번 봐보시길 추천드립니다.
webp로 변환한 이미지 사용
이미지는 PNG, JPG, JPEG 등 다양한 확장자를 가지고 있습니다. 각 확장자마다 이미지 처리 및 저장 방식이 다릅니다. 예를 들어 PNG는 벡터 기반이고, JPG는 픽셀 기반으로 이미지를 저장합니다. 그래서 PNG는 이미지 크기를 늘려도 벡터 기반이기에 이미지가 깨지지 않습니다. 반대로 JPG는 픽셀은 그대로인데 이미지가 커지기에 화질이 깨져 보입니다. 같은 이미지 사이즈라면 보통 PNG가 용량이 더 큽니다.
Webp 확장자는 구글에서 개발한 이미지 포맷으로 Web 위해 만들어진 효율적인 이미지 포맷입니다. 즉, 웹에서 이미지를 더 쉽게 호출하고 보여주기 위해 만든 포맷으로, 같은 이미지 크기 대비 파일 용량이 압도적으로 적습니다. 그래서 PNG, JPG보다 로딩 속도가 훨씬 빠릅니다. 현재 사용 중인 이미지를 Webp로 변경만 해도 속도가 빠르게 개선됩니다.
다만, 이미지를 다운 받아서 확인한다면 PNG, JPG보다 화질이 낮은 걸 확인할 수 있습니다. 그래서 이미지를 보여줄 때는 webp로 사용하고, 다운로드 기능을 쓴다면 PNG나 JPG 포맷으로 전달하는 게 좋습니다.

4. 무지성 데이터 호출

유저가 페이지를 실행하는 순간, 버블에서 Do a search for을 작동시켜서 필요한 데이터를 모두 호출합니다. 그리고 이 호출 값에 맞춰서 페이지를 로딩합니다. 즉, Do a search for이 느릴수록, 페이지 로딩도 느려집니다. 아무리 요소나 이미지를 최적화해도 데이터 호출을 최적화하지 않으면, 개선에 제한이 있을 수 밖에 없습니다. 제 경험 상으로 로딩 속도에 가장 큰 영향을 주는 건 (1) 이미지와 (2) 데이터 호출이였습니다.
데이터 호출 속도를 개선하기 위해서 아래 2가지를 고려하시면 됩니다.
Do a search for 최적화하기
데이터베이스 구조 최적화하기
Do a search for 최적화하기
Do a search for 목표 테이블을 선택하고, 해당 테이블에 constraint를 걸어서 필요한 데이터를 불러오는 오퍼레이터입니다. 이때, constraint는 최대한 큼직큼직하게 데이터를 걸러버리는 것을 사용해야 합니다. 예를 들어 1000개의 행이 있는데 여기서 10개의 행을 불러온다고 해봅시다. 그리고 아래처럼 데이터를 거를 수 있다고 합시다. 여기서 과정의 횟수는 A 방법이 B 방법보다 훨씬 많기에 데이터 호출 속도도 느려집니다.
A 방법 : 1000 → 800 → 600 → 400 → 200 → 10
B 방법 : 1000 → 500 → 10
또한, Do a search for에서 Filter 오퍼레이터를 가급적 함께 사용하지 말아야 합니다. 특정 테이블에서 데이터를 필터링해서 불러오는 방식은 크게 (1) Do a search for에서 contraint를 거는 방식과 (2) Do a search for 뒤에 filter 오퍼레이터를 추가하는 방식이 있습니다. 둘은 얼핏 보면 비슷해보이지만 전혀 다릅니다. 전자는 Do a search for과 동시에 필터링을 처리하지만, 후자는 Do a search for로 데이터를 완전히 불러온 후에 다시 후가공 필터링을 하는 방식입니다.
Do a search for에서 contraint를 거는 방식
Do a search for 뒤에 filter 오퍼레이터를 추가하는 방식
다만 그렇다고 항상 Filter 오퍼레이터를 절대적으로 사용하지 않는 건 아닙니다. Filter 오퍼레이터는 Do a search for의 Constraint와 다르게 [Advanced]라는 선택지를 제공해서 훨씬 복잡한 필터링을 가능케 합니다.
데이터베이스 구조 최적화하기
특정 테이블은 다른 테이블과 연결하는 속성을 지니고 있습니다. 예를 들어, 고객이 어떤 상품을 주문했는지를 알고 싶다면, (1) order 테이블에서 product 테이블의 데이터 타입을 지닌 필드를 생성하거나 (2) product 테이블에서 order 테이블의 데이터 타입을 지닌 필드를 생성할 수 있습니다. 여기서 저희는 어떤 방식을 선택해야 할까요?
만약 주문 페이지에서 주문한 상품 이름을 보여주고 싶다고 합시다. 우선 페이지의 type of content는 핵심이 되는 데이터의 order 테이블이 되야 합니다. 아래 2가지 선택지 중에서 1번째 데이터베이스 구조가 압도적으로 데이터 호출 속도가 빠릅니다.
1.
order 테이블에서 product 테이블의 데이터 타입을 지닌 필드를 생성
2.
product 테이블에서 order 테이블의 데이터 타입을 지닌 필드를 생성할 수 있습니다.
이는 데이터 호출 로직을 생각하면 됩니다. 1번의 경우에는 상품명을 보여주는 방식이 [current page’s order’s product’s name]을 사용하면 됩니다. 반면, 2번의 경우에는 [Do a search for product]에 constraint로 [order = current page’s order]를 사용해야 합니다. 1번의 경우에는 확인하는 레코드는 “현재 페이지의 order 레코드”와 “현재 페이지의 order 레코드에서 product 필드를 통해 확인한 product 레코드” 딱 2개 밖에 없습니다. 반면 2번의 경우에는 우선 product 테이블에 존재하는 모든 레코드를 확인해야 합니다.
이렇든 데이터베이스 구조를 어떻게 짜느냐에 따라 데이터 호출 로직의 효율성이 크게 차이납니다. 찐개발자는 항상 이런 걸 염두에 두고 있으니, 그들을 칭찬합시다!

5. 무거운 플러그인

버블에서 자체적으로 구현하기 어려운 기능들은 플러그인을 다운로드 받아서 쉽게 햇징할 수 있습니다. 참고로 이러한 플러그인은 모두 코드로 개발됩니다. 노코드 툴인 버블에 코드를 사용한다니 아이러니한 것 같습니다! 아무튼, 일부 플러그인은 외부 JS 라이브러리나 nodeJS 패키지를 사용합니다. 쉽게 말해 누군가가 만들어 둔 코드들을 불러와서 사용한다고 보시면 됩니다. 앞서 말했듯 해당 라이브러리나 패키지는 “외부”에 위치하기에 이를 호출해서 사용해야 합니다. 그래서 이 호출 때문에 속도가 느려질 수도 있습니다.
이를 해결하기 위해 아래 방법이 있습니다.
불필요한 플러그인 삭제하기
플러그인 직접 개발하기
불필요한 플러그인 삭제하기
불필요한 플러그인이 외부 라이브러리나 패키지는 불러와서 페이지 속도가 느려질 수도 있습니다. 따라서, 불필요한 플러그인은 삭제를 하는 게 좋습니다. 내가 플러그인을 쓰고 있는지 아닌지를 확인하기 위해서, 삭제 전에 검색을 하는 걸 추천드립니다.
우측 상단에 [돋보기] 아이콘을 클릭하고, [Action type]에 해당 플러그인이 제공하는 액션을 선택해 검색하면 됩니다. 플러그인이 제공하는 액션들은 플러그인 설정 페이지에서 확인할 수 있습니다.
플러그인 직접 개발하기
혹은 직접 플러그인을 개발하는 방법도 있습니다. 개발을 잘 몰라도 chatGPT가 있으면, 어느 정도 작업을 할 수 있습니다. chatGPT를 사용할 때 한 번에 모든 코드를 알아내겠다고 접근하지 않고, 순차적으로 질문을 하는 게 좋습니다. 아래 이미지를 보면, 질문을 순차적으로 해서 코드를 chatGPT가 더 상세히 만들게 하고 있습니다.
플러그인 개발 방법은 아래 블로그 링크에 정리했습니다. 또한, 플러그인을 만드는 게 어렵다면 버블박스에 요청해주세요.