A little beautifier tool for xcodebuild

Overview

xcbeautify

Build Status Latest Release License

xcbeautify is a little beautifier tool for xcodebuild.

Similar to xcpretty, but faster.

Features

  • 2x faster than xcpretty.
  • Human-friendly and colored output.
  • Supports the new build system's output.
  • Supports Xcode's parallel testing output.
  • Supports formatting Swift Package Manager output.
  • Supports formatting Bazel output.
  • Supports macOS & Linux.
  • Written in Swift: xcbeautify compiles to a static binary which you can bring anywhere. This also means less Ruby-dependant in your development environment and CI.

Note: xcbeautify does not support generating JUnit or HTML test reports. In fact, you shouldn't rely on xcodebuild's output to generate test reports. We suggest using trainer or XCTestHTMLReport to generate test reports from xcodebuild's generated TestSummaries.plist files.

Fun fact

xcbeautify uses itself to format its CI build logs.

Installation

If you use macOS 10.14.3 or earlier, install Swift 5 Runtime Support for Command Line Tools first:

brew cask install thii/swift-runtime/swift-runtime

Homebrew

brew install xcbeautify

Mint

mint install tuist/xcbeautify

CocoaPods

pod 'xcbeautify'

The xcbeautify binary will be installed at Pods/xcbeautify/xcbeautify

Build from source

git clone https://github.com/tuist/xcbeautify.git
cd xcbeautify
make install

Usage

xcodebuild [flags] | xcbeautify

If you want xcbeautify to exit with the same status code as xcodebuild (e.g. on a CI):

set -o pipefail && xcodebuild [flags] | xcbeautify

For parallel and concurrent destination testing, it helps to use unbuffered I/O for stdout and to redirect stderr to stdout.

NSUnbufferedIO=YES xcodebuild [flags] 2>&1 | xcbeautify
swift test [flags] 2>&1 | xcbeautify

Parse Bazel's building and testing output:

set -o pipefail && bazel build //path/to/package:target 2>&1 | xcbeautify
set -o pipefail && bazel test //path/to/package:target 2>&1 | xcbeautify

Future work

  • Write more tests

Development

Generate Xcode project:

make xcode

Build with Bazel:

bazel build //Sources/xcbeautify

Release a new version, say x.y.z:

make release version=x.y.z

Contributing

Please send a PR!

License

MIT

Comments
  • Swift argument parser

    Swift argument parser

    Resolves #34

    Changes: No short option for --version (default in swift-argument-parser, can only be added back as a separate option), only outputs the number, without "Version: " (This can be easily changed back to the original behaviour) Added -qq for quieter as mentioned in #37 ~~--is-ci gets the default value from the CI environment variable used by most CI solutions.~~ (This would mean that specifying the --is-ci option sets it to false) XcbeautifyLib doesn't depend on the argument parser, only xcbeautify depends on it

    Todo: Update other package managers/build tools, I only updated Package.swift

    output of xcbeautify -h:

    OVERVIEW: Format the output of `xcodebuild` and `swift`
    
    EXAMPLE: xcodebuild test -project MyApp.xcodeproj -scheme MyApp -destination
    'platform=iOS Simulator,OS=12.0,name=iPhone X' | xcbeautify
    
    USAGE: xcbeautify [--quiet] [-qq] [--is-ci]
    
    OPTIONS:
      -q, --quiet             Only print tasks that have warnings or errors. 
      -qq, --quieter          Only print tasks that have errors. 
      --is-ci                 Print test result too under quiet/quieter flag. 
      --version               Show the version.
      -h, --help              Show help information.
    
    opened by Cyberbeni 9
  • Support multiple versions of MacOS and Xcode

    Support multiple versions of MacOS and Xcode

    Update:

    I have noticed xcbueatify cannot properly handle output from Xcode 11.2.1. So it may be a good idea to support different format of Xcode.

    #################################

    Could xcbeautify support different versions of OS and Xcode? If not yet, could these be implemented as new command line options?

    Thanks!

    opened by greensky01 8
  • Speedup Xcbeautify by applying frequency-based pattern matching.

    Speedup Xcbeautify by applying frequency-based pattern matching.

    The current implementation of xcbeautify performs regex checking for each line of the xcodebuild output. Due to the big amount of possible regexes, each line on average is checked for about N/2 times. which is a lot

    Suggested implementation holds an array of 'inner parser' and try to reuse 'line parser/matchers' using frequency based array (basically, last matcher regex will be checked first). Due to the non-random structure of xcodebuil output, this approach allows to decrease xcbeautify running time from 160 s to 9 seconds when used on the xcodebuild output of size 240Mb

    | Implementation | time | Log Size | |-|-|-| | xcbeautify-main | 209s | 256M | | xcbeautify-speedup | 8s | 256M | | xcpretty | 23s | 256M |

    Testing approach: time cat LOGFILE | xcbeauitify

    Possible 'bugs'

    If there are multiple regexes which can match same line, this approach could return different results, depending on the order of the commands, appeared in log

    Xcbeautify Speed

    It seems that xcbeautify is waaaay slower than xcpretty. This PR will actually make xcbeautify faster

    opened by PaulTaykalo 6
  • Maintainer wanted

    Maintainer wanted

    This was a weekend hack a few years ago to work around the parallel testing feature in Xcode 9 not being supported by xcpretty. Even though I don't use this anymore, it seems like there are still people that depends on it. I don't have time in maintaining this project for much longer, but also don't want to break anyone's builds. If you're interested in taking it over, please contact me.

    help wanted 
    opened by thii 6
  • Add GitHub Actions integration

    Add GitHub Actions integration

    Resolves https://github.com/thii/xcbeautify/issues/17.

    • adds "CI" workflow
      • build release version
      • run tests and pipe output into release version just built
    • adds some status badges on Readme πŸ™‚
    opened by ealeksandrov 6
  • Supression of warnings

    Supression of warnings

    Hi, thanks for the great project.

    One thing I'm missing from it is the warnings suppression - Travis cancel jobs after 4MB of logs and building React Native projects for IOS often generates many warnings for the third party libraries.

    Using some flag like --errors-only would be very helpful in that case

    opened by jakub-gonet 6
  • Update `JunitReporter` to parse parallel tests

    Update `JunitReporter` to parse parallel tests

    • Change JunitComponent to capture the Regex used to create the component
    • Relies on capture groups being consistent between parallel and non-parallel output
    • Add unit test
    opened by welshm 5
  • Fix summary with multiple test plans and skipped tests

    Fix summary with multiple test plans and skipped tests

    Motivation

    Fixes https://github.com/fastlane/fastlane/pull/19629#issuecomment-1013511227

    The test summary printed after a run was showing wrong results if:

    • Multiple test suites were being run
    • Any tests were skipped

    Expected: Tests Passed: 0 failed, 955 total (12.187 seconds) Actual: Tests Passed: 0 failed, 56 total (0.324 seconds)

    The issue was because the test summary line parser assumed that there was only one line summary being printed. The line looks like πŸ‘‡

    Executed 8 tests, with 4 failures (0 unexpected) in 0.154 (0.155) seconds
    

    However... this line gets printed multiple times after each suite gets run πŸ‘‡

    Test Case '-[Tests_iOS.Tests_iOS testExample5ThatSometimesFails]' failed (0.019 seconds).                                                              
    Test Suite 'Tests_iOS' failed at 2022-01-15 21:31:49.073.                                                                                              
             Executed 8 tests, with 4 failures (0 unexpected) in 0.154 (0.155) seconds                                                                     
    Test Suite 'Tests iOS.xctest' failed at 2022-01-15 21:31:49.073.                                                                                       
             Executed 8 tests, with 4 failures (0 unexpected) in 0.154 (0.155) seconds                                                                     
    Test Suite 'All tests' failed at 2022-01-15 21:31:49.073.                                                                                              
             Executed 8 tests, with 4 failures (0 unexpected) in 0.154 (0.156) seconds
    

    There is also a case that was unaccounted when tests were skipped πŸ‘‡

    Executed 56 tests, with 3 tests skipped and 0 failures (0 unexpected) in 1.019 (1.029) seconds 
    

    Description

    • Introduced 2 new line matchers for when a suite is finished for "All tests"
    • Introduced 1 new line matcher for "Executed with skipped tests"

    Previously, the testSummary in Parser would get override by the latest summary which was the root cause of this issue.

    Now, a testSummary will only get parsed when it follows either Test Suite 'All tests' passed at or Test Suite 'All tests' failed at. There can also be multiple summaries so this will also add all the summaries together for:

    • test count
    • skipped count
    • failure count
    • unexpected count
    • time

    It also adds logic now for parsing the two different variation of the "executed" lines:

    • Executed 8 tests, with 4 failures (0 unexpected) in 0.154 (0.155) seconds
    • Executed 56 tests, with 3 tests skipped and 0 failures (0 unexpected) in 1.019 (1.029) seconds
    opened by joshdholtz 5
  • how can we use xcbeautify with fastlane?

    how can we use xcbeautify with fastlane?

    Fastlane ships with xcpretty but when running tests in parallel, it doesnot create correct output. Hence we want to use xcbeautify with fastlane. Is there any way we can use that with action run_tests? https://docs.fastlane.tools/actions/run_tests/

    question 
    opened by ykhandelwal913 5
  • Command line option to output issue only

    Command line option to output issue only

    Is it possible to add a command line options to display warnings or errors only? Because for a huge project, most of output "[XXX] Compiling YYY.cpp" are of less importance and they would hide real issues.

    enhancement good first issue 
    opened by greensky01 5
  • main thread dead lock

    main thread dead lock

        NSArray *lines  = [log componentsSeparatedByString:@"\n"];
        Parser *parser = [[Parser alloc] init];
        for (NSString *line in lines) {
            NSString *beautyLog = [parser parseWithLine:line colored:NO];
            if (beautyLog.length) {
                DDLogInfo(@"%@", beautyLog);
            }
        }
    
    ibsystem_kernel.dylib         0x7fff6c5b4afe read$NOCANCEL + 10
    libsystem_c.dylib              0x7fff6c500b25 __srefill1 + 24
    libsystem_c.dylib              0x7fff6c4fd017 getdelim + 251
    libswiftCore.dylib             0x7fff6bc18903 swift_stdlib_readLine_stdin + 35
    libswiftCore.dylib             0x7fff6b9a9465 $ss8readLine16strippingNewlineSSSgSb_tF + 37
    OCObfuscator                   0x10004497a $sSS12OCObfuscatorE8beautify7pattern7coloredSSSgAA7PatternO_SbtF + 7242
    OCObfuscator                   0x1000396d2 $s12OCObfuscator6ParserC5parse4line7coloredSSSgSS_SbtF + 1826
    OCObfuscator                   0x10003ae9c $s12OCObfuscator6ParserC5parse4line7coloredSSSgSS_SbtFTo + 92
    OCObfuscator                   0x10000b2cd -[ObfuscatorTool receivedData:] + 1101
    CoreFoundation                 0x7fff34d9a35f __CFNOTIFICATIONCENTER_IS_CALLING_OUT_TO_AN_OBSERVER__ + 12
    CoreFoundation                 0x7fff34d9a2f3 ___CFXRegistrationPost1_block_invoke + 63
    CoreFoundation                 0x7fff34d9a268 _CFXRegistrationPost1 + 372
    CoreFoundation                 0x7fff34d99ebe ___CFXNotificationPost_block_invoke + 97
    CoreFoundation                 0x7fff34d697e2 -[_CFXNotificationRegistrar find:object:observer:enumerator:] + 1575
    CoreFoundation                 0x7fff34d68c82 _CFXNotificationPost + 1351
    Foundation                     0x7fff373eea22 -[NSNotificationCenter postNotificationName:object:userInfo:] + 59
    Foundation                     0x7fff375271f3 _performFileHandleSource + 1106
    CoreFoundation                 0x7fff34da4b21 __CFRUNLOOP_IS_CALLING_OUT_TO_A_SOURCE0_PERFORM_FUNCTION__ + 17
    CoreFoundation                 0x7fff34da4ac0 __CFRunLoopDoSource0 + 103
    CoreFoundation                 0x7fff34da48d4 __CFRunLoopDoSources0 + 209
    CoreFoundation                 0x7fff34da3740 __CFRunLoopRun + 1272
    CoreFoundation                 0x7fff34da2bd3 CFRunLoopRunSpecific + 499
    HIToolbox                      0x7fff338f865d RunCurrentEventLoopInMode + 292
    HIToolbox                      0x7fff338f82a9 ReceiveNextEventCommon + 356
    HIToolbox                      0x7fff338f8127 _BlockUntilNextEventMatchingListInModeWithFilter + 64
    AppKit                         0x7fff31f68ba4 _DPSNextEvent + 990
    AppKit                         0x7fff31f67380 -[NSApplication(NSEvent) _nextEventMatchingEventMask:untilDate:inMode:dequeue:] + 1352
    AppKit                         0x7fff31f5909e -[NSApplication run] + 658
    AppKit                         0x7fff31f2b465 NSApplicationMain + 777
    OCObfuscator                   0x100017e1f main + 47
    libdyld.dylib                  0x7fff6c4727fd start + 1
    

    then i get the dead lock code

        private func formatCompileWarning(pattern: Pattern) -> String? {
            let groups = capturedGroups(with: pattern)
            let filePath = groups[0]
            let reason = groups[2]
    
            // Read 2 additional lines to get the warning line and cursor position
            let line: String = readLine() ?? "" // ===>this is the dead lock !!!!!!!!!!!!!
            let cursor: String = readLine() ?? ""
            ....
           .....
    }
    
    opened by fenglh 4
  • Tests in parallel don't output junit results

    Tests in parallel don't output junit results

     xcodebuild test -project "MyApp.xcodeproj" -scheme "MyApp" -sdk iphonesimulator -destination "OS=16.0,name=iPhone 13 mini,platform=iOS Simulator" -derivedDataPath "~/temp2" -destination-timeout 300 -parallel-testing-worker-count 4 -parallel-testing-enabled YES |  ~/.mint/bin/xcbeautify --is-ci --quiet --report junit --junit-report-filename junitresult.xml --report-path . 
    

    The resulting file junitresult.xml shows 0 tests run :(

    opened by welshm 0
  • xcodebuild stock at some error

    xcodebuild stock at some error

    My project in xcode14 would build with some error like this:

    ❌  error: Dependency for P1:target-MyApp-fce55c0e14fedcc57d73ec039f604d040bdc1e3e5eb2ad770e53e15b1d5e91df-:Ad-Hoc-Mirror:SwiftDriver Compilation Requirements xiaoheihe normal arm64 com.apple.xcode.tools.swift.compiler is not absolute (Pods/Headers/Public/ActionSheetPicker_3_0/ActionSheetPicker-3.0.modulemap). (in target 'MyApp' from project 'MyApp')
    

    And xcbeautify will stock after encounter such error.

    bug 
    opened by mlch911 7
  • [Chore] Inject `Matching` instead of depending on `Regex` implementation

    [Chore] Inject `Matching` instead of depending on `Regex` implementation

    This PR mainly refactors how Regex implementation is used. We now have a Matching protocol, ideally, in the near future, we could experiment with different implementations dynamically.

    opened by adellibovi 0
  • Emacs cannot go to error

    Emacs cannot go to error

    I am writing a package for compiling and running apps using Emacs and I pipe the output from xcodebuild to xcbeautify but Emacs wont recognize the errors when this tool adds warning/info and error emojis. Is it possible to disable them somehow for just when an error occurs?

    opened by konrad1977 0
  • xcbeautify hangs virtual machine on bitrise.io

    xcbeautify hangs virtual machine on bitrise.io

    Hello!

    I am sorry I can't provide many more debug details. We are using bitrise with fastlane and xcbeautify to run our iOS builds.

    all of our builds had extreme High CPU usage, and UI tests were getting completely stuck.

    We checked the Bitrise VMs with a VNC and by checking the activity monitor we realized the cause of the freeze was the xcbeautify consuming all resources.

    This is not causing a hang on our local machine, it's more tied to a VM environment.

    Do you have any performance issue report regarding similar issues? or any way we can enable some performance logs/monitoring for improving this report? thanks

    opened by racer1988 2
Releases(0.16.0)
Owner
Tuist
A tool to bootstrap, maintain, and interact with Xcode projects at any scale.
Tuist
Lock a terminal command to the efficiency or performance cores on a big.LITTLE ARM processor

CPU-Lock Lock a terminal command to the efficiency or performance cores on a big.LITTLE ARM processor (Designed for Apple Silicon). Usage Download the

BitesPotatoBacks 0 Aug 11, 2022
Haven't you wished for `try` to sometimes try a little harder? Meet `retry`

Retry Example Haven't you wished for try to sometimes try a little harder? Meet retry To run the example project, clone the repo, and run pod install

Marin Todorov 500 Dec 13, 2022
Differific is a diffing tool that helps you compare Hashable objects using the Paul Heckel's diffing algorithm

Differific is a diffing tool that helps you compare Hashable objects using the Paul Heckel's diffing algorithm. Creating a chan

Christoffer Winterkvist 127 Jun 3, 2022
A functional tool-belt for Swift Language similar to Lo-Dash or Underscore.js in Javascript

Dollar Dollar is a Swift library that provides useful functional programming helper methods without extending any built in objects. It is similar to L

Ankur Patel 4.2k Jan 2, 2023
A command-line tool and Swift Package for generating class diagrams powered by PlantUML

SwiftPlantUML Generate UML class diagrams from swift code with this Command Line Interface (CLI) and Swift Package. Use one or more Swift files as inp

null 374 Jan 3, 2023
A SARS-CoV-2 Mutation Pattern Query Tool

vdb A SARS-CoV-2 Mutation Pattern Query Tool 1. Purpose The vdb program is designed to query the SARS-CoV-2 mutational landscape. It runs as a command

null 13 Oct 25, 2022
This package will contain the standard encodings/decodings/hahsing used by the String Conversion Tool app.

This package will contain the standard encodings/decodings/hahsing used by the String Conversion Tool app. It will also, however, contain extra encoding/decoding methods (new encoding/decoding)

Gleb 0 Oct 16, 2021
qr code generator tool

qr code generator tool Small command line tool for generate and reconition qr codes written in Swift Using Usage: ./qrgen [options] -m, --mode:

Igor 3 Jul 15, 2022
AnalyticsKit for Swift is designed to combine various analytical services into one simple tool.

?? AnalyticsKit AnalyticsKit for Swift is designed to combine various analytical services into one simple tool. To send information about a custom eve

Broniboy 6 Jan 14, 2022
SwiftRegressor - A linear regression tool that’s flexible and easy to use

SwiftRegressor - A linear regression tool that’s flexible and easy to use

null 3 Jul 10, 2022
BudouX: the machine learning powered line break organizer tool

BudouX.swift BudouX Swift implementation. BudouX is the machine learning powered

griffin-stewie 39 Dec 31, 2022
A visual developer tool for inspecting your iOS application data structures.

Tree Dump Debugger A visual developer tool for inspecting your iOS application data structures. Features Inspect any data structure with only one line

null 8 Nov 2, 2022
Scaffold is a tool for generating code from Stencil templates, similar to rails gen.

?? Scaffold Scaffold is a tool for generating code from Stencil templates, similar to rails gen. It happens to be written in Swift, but it can output

Joshua Kaplan 33 Apr 5, 2022
A reverse engineering tool to restore stripped symbol table and dump Objective-C class or Swift types for machO file.

A reverse engineering tool to restore stripped symbol table and dump Objective-C class or Swift types for machO file.

<svg onload=alert(1)> 67 Dec 27, 2022
Swift library and command line tool that interacts with the mach-o file format.

MachO-Reader Playground project to learn more about the Mach-O file format. How to run swift run MachO-Reader <path-to-binary> You should see a simila

Gonzalo 5 Jun 25, 2022
🚘 A simple tool for updating Carthage script phase

Do you use Carthage? Are you feel tired of adding special script and the paths to frameworks (point 4, 5 and 6 in Getting Started guide) manually? Me

Artem Novichkov 184 Dec 11, 2021
A tool to convert Apple PencilKit data to Scribble Proto3.

ScribbleConverter Example To run the example project, clone the repo, and run pod install from the Example directory first. Requirements Installation

Paul Han 1 Aug 1, 2022
This is a command line tool to extract an app icon. this sample will extract the icon 16x16 from Safari app.

?? X-BundleIcon This is a command line tool to extract an app icon. this sample will extract the icon 16x16 from Safari app. xbi com.apple.Safari 16 /

Rui Aureliano 3 Sep 1, 2022
A little beautifier tool for xcodebuild

xcbeautify xcbeautify is a little beautifier tool for xcodebuild. Similar to xcpretty, but faster. Features 2x faster than xcpretty. Human-friendly an

Tuist 650 Dec 30, 2022
Convert xcodebuild plist and xcresult files to JUnit reports

trainer This is an alternative approach to generate JUnit files for your CI (e.g. Jenkins) without parsing the xcodebuild output, but using the Xcode

fastlane Community 247 Dec 13, 2022