AWS 기술 블로그

티니어의 AWS Device Farm을 활용한 디바이스 테스트 자동화 사례

티니어(Tnear)‘불편을 민감하게, 변화는 과감하게’라는 미션을 달성하기 위해, 생활 유틸 앱을 개발하고 서비스하는 기업입니다. 누구나 쉽게 쓸 수 있는 기능을 어떻게 만들지 항상 고민하며, 첫 화면 날씨, 디자인 키보드, 말하는 번역 등 각 분야의 1위 앱을 사용자들에게 제공하고 있습니다. 또한 1000만 다운로드를 기록한 앱, 국내를 넘어 200개의 국가로 나아가는 앱까지 서비스하며 매년 200% 이상 성장하고 있습니다.

본 글은 티니어가 사용자의 만족도를 높이고 사용자에게 최상의 경험을 제공하기 위해 AWS Device Farm을 활용하여 기존 디바이스 테스트 프로세스를 자동화하고 개선한 과정을 소개합니다.

기존 디바이스 테스트 프로세스의 문제

티니어는 높은 사용자 만족을 목표로 다양한 디바이스에서 안정적으로 앱이 작동하도록 지속적인 노력을 기울여왔습니다. 초기에는 수동 테스트로 진행되었으며 이러한 수동 테스트의 효율성을 높이기 위해 여러 개선 방안을 도입했습니다. 먼저 휴먼 에러를 줄이기 위해 테스트 체크리스트를 구체화하고, 테스트 과정을 매뉴얼화 했습니다. 또한 조직 내에서의 빠른 피드백 프로세스를 위해 개발자와 QA 팀 간의 협업을 강화했습니다. 이런 개선방법을 통해 일부 목표를 달성했으나, 수동 테스트의 근본적인 한계로 인해 여전히 다음과 같은 어려움을 가지고 있었습니다.

  1. 수동 테스트의 의존성
    수동 테스트에 의존하고 있어 테스트 과정에 많은 시간과 리소스가 소모되었으며, 특히 휴먼 에러로 인한 이슈들이 종종 발생했습니다. 테스트 과정에서 발견하지 못한 오류는 사용자 경험에 부정적인 영향을 미칠 수 있을 뿐 아니라, 배포 후 신속한 수정이 필요하기 때문에 리소스 소모가 더 컸습니다. 따라서 테스트 과정에 쓰이는 리소스를 줄이며 오류 검출률을 향상할 수 있는 방법이 필요했습니다.
  2. 불필요하게 반복되는 테스트
    테스트 중 간단한 UI 오류나 기본적인 기능 오류가 발견되면 이를 수정한 다음, 오류가 발생한 컴포넌트 뿐 아니라 수정이 미치는 영향 전체를 수동으로 다시 확인해야 했습니다. 즉, 이전에 확인한 컴포넌트도 다시 확인해야 했기 때문에 개발자와 테스트자 모두에게 큰 부담으로 작용했으며, 이로 인한 리소스가 낭비되지 않기를 원했습니다.
  3. 멀티 플랫폼 디바이스 테스트의 번거로움
    AOS 및 iOS 멀티 플랫폼을 지원하는 앱을 테스트하기 위해서는 특정 디바이스를 직접 구매하여 테스트해야 했습니다. 이는 시간과 비용 측면에서 비효율적이었고, 디바이스 수급의 어려움으로 인해 테스트가 지연되는 경우도 발생했습니다.

AWS Device Farm을 통한 디바이스 테스트 자동화 고려

수동 테스트의 한계를 극복하고 보다 효율적인 테스트 프로세스를 도입하기 위해, 티니어는 자동화된 테스트를 고려하게 되었습니다. 그 과정에서 AWS Device Farm을 솔루션으로 선택하게 되었습니다.

AWS Device Farm이란?

AWS Device Farm은 테스트 인프라를 프로비저닝 하고, 관리하지 않아도 다양한 브라우저 및 실제 모바일 디바이스에서 테스트를 진행하여 웹 및 모바일 앱 품질을 향상하는 애플리케이션 테스트 서비스입니다. 특히, 모바일 애플리케이션 개발을 하고 있다면, 실제 여러 디바이스에서 동시에 테스트를 실행함으로써 테스트 도구 실행속도를 높이고, 비디오 및 로그를 생성하여 앱과 관련된 문제를 빠르게 식별할 수 있습니다.

또한, 개발자 친화적인 테스트 환경을 위해 스크립팅이 필요없는 AWS 내장 테스트 도구를 실행하거나, Appium, Calabash 및 Espresso와 같은 다양한 오픈 소스 테스트 프레임워크를 선택하여 테스트를 사용자 정의 할 수 있습니다. 이뿐 아니라, AWS의 서비스 플러그인과 API를 사용하여 테스트를 자동으로 시작하고 Android Studio와 Jenkins 같은 지속적 통합 환경 및 IDE와 통합하여 개발 워크플로우를 구축할 수 있습니다.

AWS Device Farm의 보안 우수성

AWS Device Farm은 안전한 모바일 앱 테스트 환경을 제공하기 위해 다양한 보안 기능을 갖추고 있습니다. 먼저, AWS의 견고한 클라우드 인프라를 기반으로 구축되어 있어 물리적 보안부터 네트워크 보안, 그리고 접근 제어까지 AWS의 포괄적인 보안 체계를 자연스럽게 활용할 수 있습니다.

특히 주목할 만한 점은 테스트 환경의 철저한 격리입니다. 각각의 테스트는 완전히 독립된 환경에서 실행되어, 테스트 간의 상호 간섭이나 데이터 유출 위험을 원천적으로 차단합니다. 따라서, 이는 테스트의 신뢰성 뿐 아니라 보안도 함께 보장합니다. 테스트 과정에서 발생하는 민감한 데이터는 AWS Device Farm의 강력한 보안 메커니즘으로 보호됩니다. 데이터는 전송 중에도, 저장 시에도 암호화되며, 접근 권한이 있는 사용자만 이 데이터를 조회할 수 있습니다.

또한, AWS는 지속적으로 보안 업데이트를 제공하여 최신 보안 위협에 대응합니다. 사용자는 별도의 보안 관리 작업없이도 항상 최신의 보안 상태를 유지할 수 있습니다. 마지막으로, AWS IAM을 통한 중앙화된 접근 제어는 보안 관리의 효율성을 높입니다. 조직은 세밀한 권한 설정으로 리소스에 대한 접근을 통제할 수 있으며, 이는 전체적인 보안 거버넌스 강화로 이어집니다. 이러한 다층적인 보안 기능들이 유기적으로 작동하며, AWS Device Farm은 기업들이 안심하고 사용할 수 있는 신뢰성 높은 테스트 플랫폼으로 자리매김하고 있습니다.

AWS Device Farm 도입을 결심한 이유

  1. 다양한 실제 디바이스에서의 테스트 가능
    AWS Device Farm은 다양한 실제 디바이스에서 앱을 테스트할 수 있는 기능을 제공합니다. 이를 통해 여러 환경에서 앱이 어떻게 작동하는지 검증할 수 있었고, 보다 신뢰성있는 테스트 결과를 얻을 수 있었습니다.
  2. 기존 툴과의 원활한 통합
    Appium과 같은 오픈 소스 툴과의 통합이 원활하여, 이미 작성 중이던 자동화 스크립트를 쉽게 활용할 수 있었습니다. 이는 기존 워크플로우에 큰 변화를 주지 않고도 자연스럽게 자동화 테스트를 도입할 수 있도록 했습니다.
  3. 자동화 테스트 결과를 통한 빠른 피드백
    테스트가 완료된 후 상세한 보고서와 결과 데이터를 제공하여, 문제 발생 시 빠르게 피드백을 받을 수 있었습니다. 이를 통해 디버깅 및 수정 과정을 보다 효율적으로 진행할 수 있었으며, 불필요한 사이클 반복을 줄이는 데 큰 도움이 되었습니다.

AWS Device Farm을 통한 디바이스 테스트 자동화 솔루션 구축

티니어에서 배포를 위해 사용하고 있는 Fastlane은 iOS 및 Android 클라이언트 배포 과정을 자동화하는 오픈소스 라이브러리로 빌드, 테스트, 배포 등 반복적인 과정을 간편하게 관리할 수 있게 해 주는 도구입니다. 기존 파이프라인에서 앱을 배포하기 전에 AWS Device Farm을 통해 UI 테스트를 하는 과정을 새롭게 추가하게 되었습니다. 현재 Fastlane에서 제공하는 플러그인 중 AWS Device Farm 플러그인은 없기 때문에 직접 스크립트를 작성해 자동화를 진행하게 되었습니다.

구현 상세

Fastlane에서 AWS Device Farm 실행 과정은 아래와 같습니다.

  1. APK 파일을 AWS Device Farm에 업로드
  2. AWS Device Farm에 QA가 최신 업로드한 테스트 코드 파일의 ARN 가져오기
  3. AWS Device Farm 테스트 실행

예제 코드

def runUiTest(versionName)
    # Device Farm 클라이언트 생성
    client = Aws::DeviceFarm::Client.new

    # 테스트 실행에 필요한 매개변수 설정
    project_arn = ENV['PROJECT_ARN']   
    device_pool_arn = ENV['DEVICE_POOL_ARN']
    test_spec = ENV['TEST_SPEC_ARN']

    locale = 'ko_KR'  # 사용할 언어 설정

    # APK 파일 업로드
    upload = client.create_upload({
      project_arn: project_arn,
      name: File.basename(lane_context[SharedValues::GRADLE_APK_OUTPUT_PATH]),
      type: 'ANDROID_APP',
      content_type: 'application/octet-stream'
    }).upload

    upload(upload, lane_context[SharedValues::GRADLE_APK_OUTPUT_PATH])
    UI.message 'AWS Device Farm에 APK 파일 업로드 중... ☕️'
    upload = wait_for_upload(client, upload)
    raise 'APK 파일 업로드 실패. 🙈' unless upload.status == 'SUCCEEDED'

    # 업로드 리스트 가져오기
    uploads = client.list_uploads({
      arn: project_arn,
      type: 'APPIUM_PYTHON_TEST_PACKAGE' # 업로드 타입 설정
    })

    # 업로드 리스트를 업로드 날짜 기준으로 정렬
    sorted_uploads = uploads.uploads.sort_by(&:created)

    # 가장 최근에 업로드된 파일의 ARN 가져오기
    latest_upload_arn = sorted_uploads.last&.arn
    latest_upload_file_name = sorted_uploads.last&.name

    # 최근에 업로드된 파일의 ARN 출력
    puts "테스트에 사용할 코드 파일 이름: #{latest_upload_file_name}"

    # 테스트 실행 요청 생성
    test_run_response = client.schedule_run({
      project_arn: project_arn,
      app_arn: upload.arn,
      device_pool_arn: device_pool_arn,
      name: "#{versionName}",
      test: {
        type: 'APPIUM_PYTHON', # 테스트 유형 설정
        test_package_arn: latest_upload_arn,
        test_spec_arn: test_spec
      },
      configuration: {
        locale: locale,
        location: {  # 위치 설정 추가
          latitude: latitude,
          longitude: longitude
        }
      },
       execution_configuration: {
           jobTimeoutMinutes: 70,
           accountsCleanup: true,
           appPackagesCleanup: true,
           videoCapture: true
       }
    })
end

def upload(upload, path)
     url = URI.parse(upload.url)
     contents = File.open(path, 'rb').read
     Net::HTTP.new(url.host).start do |http|
       http.send_request("PUT", url.request_uri, contents, { 'content-type' => 'application/octet-stream' })
     end
 end

 def fetch_upload_status(client, upload)
     client.get_upload({
       arn:  upload.arn
     }).upload
 end

 def wait_for_upload(client, upload)
     upload = fetch_upload_status(client, upload)
     while upload.status == 'PROCESSING' || upload.status == 'INITIALIZED'
       sleep 10
       upload = fetch_upload_status(client, upload)
     end

     upload
 end

AWS Device Farm을 통한 자동화 테스트가 완료되면, 테스트 결과를 Slack으로 실시간 알림을 받을 수 있게 구성했습니다. 테스트 종료 시 성공 또는 실패 여부를 Slack 채널에서 알 수 있게 되었기 때문에, 팀이 즉각적으로 테스트 결과를 공유받고 대응할 수 있게 되었습니다.

개선 결과 및 향후 계획

AWS Device Farm을 활용하여 기존 디바이스 테스트 프로세스를 자동화하고 개선할 수 있었습니다. 수치화한 개선 결과는 다음과 같습니다.

  1. 본격적인 QA에 들어가기 전, 문제를 사전 발견하는 비율이 약 30% 증가했으며, 이는 다양한 환경에서의 문제 상황을 조기에 식별하는 데 큰 도움이 되었습니다.
  2. 수동 테스트를 자동화한 결과, 테스트 시간이 60% 이상 단축되었습니다. 이를 통해 개발 및 QA 팀은 더 빠르게 피드백을 받을 수 있었고, 제품 출시 주기도 크게 개선되었습니다. 과거에는 평균 3일이 소요 되었던 테스트 과정이 이제는 하루 이내에 완료될 수 있습니다.
  3. 실제 디바이스를 구매하고 유지보수하는 비용이 25% 이상 절감되었습니다. AWS Device Farm을 통해 추가적인 디바이스 구매 없이도 다양한 디바이스에서의 테스트를 효과적으로 수행할 수 있었습니다.
  4. 사람에 의한 실수 가능성을 줄여 보다 정확한 테스트 결과를 제공하였습니다. 이로 인해, 문제 식별 속도가 약 17% 빨라졌으며, 수정 및 재배포 주기 또한 크게 향상되었습니다. 결과적으로, 최종 제품의 품질이 눈에 띄게 향상되었습니다.

또한, 자동화 파이프라인을 구축하는 것에 그치지 않고, 정기적으로 테스트 과정에 대한 회고를 진행하여 자동화된 테스트 파이프라인의 성능을 평가하고 개선 가능한 부분을 논의하고 있습니다. 예를 들어, 자동화된 테스트에서의 이슈 누락률, 테스트 시간의 단축 방안 등을 점검하여 파이프라인 고도화를 지속적으로 진행하고 있습니다. 특히, 고도화 과정에서 다양한 디바이스와 운영체제에서의 테스트 케이스를 더욱 구체적으로 작성하고 자동화하여, 각 사용자 환경에 맞는 검증을 수행하고 앱의 호환성을 높일 계획입니다.

마무리

티니어의 디바이스 테스트 자동화 파이프라인은 AWS Device Farm 도입을 통해 기존의 테스트 방법론이 안고 있던 문제들을 해결하고자 했습니다. 기존 프로세스에서는 서비스하고 있는 생활 유틸리티 앱을 다양한 장치와 운영체제 환경에서 안정적으로 동작시키기 위해 모든 장치에서 발생할 수 있는 문제를 포괄적으로 검토하는 것이 어렵고, 테스트 과정에서도 많은 시간이 소요되었습니다. 이러한 문제를 해결하기 위해 AWS Device Farm을 활용해 테스트를 자동화함으로써 시간과 비용을 절감하는 성과를 거두었습니다. 또한, 도입 과정에서 다양한 장치와 운영체제에서의 테스트 수행, 정확한 결과 수집, 그리고 자동화된 프로세스 구축과 같은 여러 요소들을 고려하게 되었습니다. 결과적으로 AWS 서비스를 기반으로 파이프라인을 고도화하며 앱의 신뢰성과 품질을 높이고, 사용자 경험을 크게 향상시킬 수 있게 되었습니다.

Beomjin Kim

김범진

김범진 개발자는 티니어에서 안드로이드 개발자로 근무하며, 다양한 앱 개발을 담당하고 있으며 자동화 프로세스 개선에도 같이 힘쓰고 있습니다.

Hyungseob Han

한형섭

한형섭 엔지니어는 티니어에서 소프트웨어 품질을 높이는 QA 엔지니어로 근무하며, 테스트 자동화와 프로세스 개선을 통해 더 나은 사용자 경험을 만드는 데 열정을 가지고 있습니다. 언제나 더 효율적이고 신뢰할 수 있는 제품을 제공하기 위해 노력합니다.

Junwon So

소준원

소준원 개발자는 티니어에서 백엔드 개발자로 근무하며, 안정적이고 확장 가능한 시스템 설계를 지향합니다. 주로 Java와 Spring Framework를 사용하여 RESTful API와 데이터베이스 연동을 개발해 왔습니다.

Jungwoo Song

Jungwoo Song

송정우 솔루션즈 아키텍트는 IT 인프라 스트럭처와 소프트웨어 서비스 개발 경험을 바탕으로, 고객의 비즈니스 성과 달성을 위해 고객과 함께 최적의 아키텍처를 구성하는 역할을 수행하고 있습니다.