From 26be54c556e29f3ad96d33c16fedfd5104c2a9cb Mon Sep 17 00:00:00 2001 From: ndubkov-distcotech Date: Tue, 6 Aug 2024 09:46:15 +0200 Subject: [PATCH] ci(bank-sdk): Update detekt and adjust for Compose (#518) ci(bank-sdk): Update detekt version and baselines. Generate default detekt config. Adjust detekt for compose --- bank-sdk/example-app/detekt-baseline.xml | 9 +- bank-sdk/sdk/detekt-baseline.xml | 33 +- capture-sdk/sdk/detekt-baseline.xml | 65 +- config/detekt/detekt.yml | 788 +++++++++++++++++++++++ gradle/libs.versions.toml | 2 +- 5 files changed, 864 insertions(+), 33 deletions(-) create mode 100644 config/detekt/detekt.yml diff --git a/bank-sdk/example-app/detekt-baseline.xml b/bank-sdk/example-app/detekt-baseline.xml index b4d4b9720..1fcd66050 100644 --- a/bank-sdk/example-app/detekt-baseline.xml +++ b/bank-sdk/example-app/detekt-baseline.xml @@ -2,7 +2,7 @@ - ComplexMethod:ConfigurationViewModel.kt$ConfigurationViewModel$fun configureGiniBank(context: Context) + CyclomaticComplexMethod:ConfigurationViewModel.kt$ConfigurationViewModel$fun configureGiniBank(context: Context) EmptyFunctionBlock:CustomOnButtonLoadingIndicatorAdapter.kt$CustomOnButtonLoadingIndicatorAdapter${} LongMethod:ConfigurationActivity.kt$ConfigurationActivity$private fun setConfigurationFeatures() LongMethod:ConfigurationActivity.kt$ConfigurationActivity$private fun updateUIWithConfigurationObject(configuration: Configuration) @@ -81,15 +81,16 @@ NewLineAtEndOfFile:PermissionHandler.kt$net.gini.android.bank.sdk.exampleapp.core.PermissionHandler.kt NewLineAtEndOfFile:ResultWrapper.kt$net.gini.android.bank.sdk.exampleapp.core.ResultWrapper.kt NewLineAtEndOfFile:SplashActivity.kt$net.gini.android.bank.sdk.exampleapp.ui.SplashActivity.kt - SwallowedException:ExampleApp.kt$ExampleApp$catch (e: IllegalStateException) { // ignore } + SwallowedException:ExampleApp.kt$ExampleApp$e: IllegalStateException TooGenericExceptionCaught:PayActivity.kt$PayActivity$t: Throwable TooGenericExceptionCaught:ResultWrapper.kt$throwable: Throwable TooManyFunctions:ExtractionsActivity.kt$ExtractionsActivity : AppCompatActivityExtractionsAdapterInterface TooManyFunctions:MainActivity.kt$MainActivity : AppCompatActivity + UnusedParameter:ExtractionsActivity.kt$ExtractionsActivity$binding: ActivityExtractionsBinding UnusedPrivateMember:ClientBankSDKFragment.kt$ClientBankSDKFragment$private fun overrideBankSDKConfiguration() - UnusedPrivateMember:ExtractionsActivity.kt$ExtractionsActivity$binding: ActivityExtractionsBinding UnusedPrivateMember:ExtractionsActivity.kt$ExtractionsActivity$private fun hideProgressIndicator(binding: ActivityExtractionsBinding) UnusedPrivateMember:ExtractionsActivity.kt$ExtractionsActivity$private fun showProgressIndicator(binding: ActivityExtractionsBinding) - UnusedPrivateMember:MainActivity.kt$MainActivity.Companion$private const val REQUEST_CONFIGURATION = 3 + UnusedPrivateProperty:ClientCaptureSDKFragment.kt$ClientCaptureSDKFragment$val capture = GiniCapture.Builder() .setGiniCaptureNetworkService(networkService) .setFileImportEnabled(true) .setDocumentImportEnabledFileTypes(DocumentImportEnabledFileTypes.PDF_AND_IMAGES) .setQRCodeScanningEnabled(true) .setFlashButtonEnabled(true) .setMultiPageEnabled(true) .build() + UnusedPrivateProperty:MainActivity.kt$MainActivity.Companion$private const val REQUEST_CONFIGURATION = 3 diff --git a/bank-sdk/sdk/detekt-baseline.xml b/bank-sdk/sdk/detekt-baseline.xml index 232048edb..92023d97f 100644 --- a/bank-sdk/sdk/detekt-baseline.xml +++ b/bank-sdk/sdk/detekt-baseline.xml @@ -2,7 +2,7 @@ - ComplexMethod:Configuration.kt$internal fun GiniCapture.Builder.applyConfiguration(configuration: CaptureConfiguration): GiniCapture.Builder + CyclomaticComplexMethod:Configuration.kt$internal fun GiniCapture.Builder.applyConfiguration(configuration: CaptureConfiguration): GiniCapture.Builder EmptyFunctionBlock:DigitalInvoiceBottomSheet.kt$DigitalInvoiceBottomSheet${ } EmptyFunctionBlock:DigitalInvoiceScreenPresenter.kt$DigitalInvoiceScreenPresenter${ } EmptyFunctionBlock:DigitalOnboardingScreenPresenter.kt$DigitalOnboardingScreenPresenter${ } @@ -12,6 +12,20 @@ EmptyFunctionBlock:LineItemsAdapter.kt$ViewHolder.AddonViewHolder${ } EmptyFunctionBlock:TextExtensions.kt$<no name provided>${ } ForbiddenComment:DigitalInvoiceOnboardingFragment.kt$DigitalInvoiceOnboardingFragment$* You should show the `DigitalInvoiceOnboardingFragment` when the * [DigitalInvoiceFragmentListener.showOnboarding()] is called. * * Include the `DigitalInvoiceOnboardingFragment` into your layout by using the [DigitalInvoiceOnboardingFragment.createInstance()] factory method to create * an instance and display it using the [androidx.fragment.app.FragmentManager]. * * A [DigitalInvoiceOnboardingFragmentListener] instance must be available before the `DigitalInvoiceOnboardingFragment` is attached to an activity. Failing * to do so will throw an exception. The listener instance can be provided either implicitly by making the hosting Activity implement the * [DigitalInvoiceOnboardingFragmentListener] interface or explicitly by setting the listener using [DigitalInvoiceOnboardingFragment.listener]. * * Your Activity is automatically set as the listener in [DigitalInvoiceOnboardingFragment.onCreate()]. * * ### Customizing the Digital Invoice Onboarding Screen * * TODO: PPL-14: Customization guide for return assistant - Android + FunctionNaming:SkontoFragment.kt$@Composable @Preview private fun ScreenReadyStatePreviewLight() + FunctionNaming:SkontoFragment.kt$@Composable @Preview(uiMode = UI_MODE_NIGHT_YES) private fun ScreenReadyStatePreviewDark() + FunctionNaming:SkontoFragment.kt$@Composable private fun FooterSection( totalAmount: SkontoData.Amount, savedAmount: SkontoData.Amount, discountValue: BigDecimal, colors: SkontoFooterSectionColors, isBottomNavigationBarEnabled: Boolean, isSkontoSectionActive: Boolean, onBackClicked: () -> Unit, onProceedClicked: () -> Unit, modifier: Modifier = Modifier, customBottomNavBarAdapter: InjectedViewAdapterInstance<SkontoNavigationBarBottomAdapter>?, ) + FunctionNaming:SkontoFragment.kt$@Composable private fun InfoBanner( colors: SkontoSectionColors.InfoBannerColors, text: String, clickable: Boolean, onClicked: () -> Unit, modifier: Modifier = Modifier, icon: Painter = painterResource(id = R.drawable.gbs_icon_important_info), ) + FunctionNaming:SkontoFragment.kt$@Composable private fun InfoDialog( text: String, colors: SkontoInfoDialogColors, onDismissRequest: () -> Unit, modifier: Modifier = Modifier, ) + FunctionNaming:SkontoFragment.kt$@Composable private fun NavigationActionBack( onClick: () -> Unit, modifier: Modifier = Modifier, ) + FunctionNaming:SkontoFragment.kt$@Composable private fun ScreenContent( navigateBack: () -> Unit, viewModel: SkontoFragmentViewModel, modifier: Modifier = Modifier, screenColorScheme: SkontoScreenColors = SkontoScreenColors.colors(), isBottomNavigationBarEnabled: Boolean, customBottomNavBarAdapter: InjectedViewAdapterInstance<SkontoNavigationBarBottomAdapter>?, ) + FunctionNaming:SkontoFragment.kt$@Composable private fun ScreenReadyState( onBackClicked: () -> Unit, onProceedClicked: () -> Unit, state: SkontoFragmentContract.State.Ready, onDiscountSectionActiveChange: (Boolean) -> Unit, onDiscountAmountChange: (BigDecimal) -> Unit, onDueDateChanged: (LocalDate) -> Unit, onFullAmountChange: (BigDecimal) -> Unit, isBottomNavigationBarEnabled: Boolean, customBottomNavBarAdapter: InjectedViewAdapterInstance<SkontoNavigationBarBottomAdapter>?, modifier: Modifier = Modifier, screenColorScheme: SkontoScreenColors = SkontoScreenColors.colors(), onInfoBannerClicked: () -> Unit, onInfoDialogDismissed: () -> Unit, ) + FunctionNaming:SkontoFragment.kt$@Composable private fun ScreenReadyStatePreview() + FunctionNaming:SkontoFragment.kt$@Composable private fun ScreenStateContent( state: SkontoFragmentContract.State, onDiscountSectionActiveChange: (Boolean) -> Unit, onSkontoAmountChange: (BigDecimal) -> Unit, onFullAmountChange: (BigDecimal) -> Unit, onDueDateChanged: (LocalDate) -> Unit, onBackClicked: () -> Unit, onProceedClicked: () -> Unit, isBottomNavigationBarEnabled: Boolean, customBottomNavBarAdapter: InjectedViewAdapterInstance<SkontoNavigationBarBottomAdapter>?, onInfoBannerClicked: () -> Unit, onInfoDialogDismissed: () -> Unit, modifier: Modifier = Modifier, screenColorScheme: SkontoScreenColors = SkontoScreenColors.colors() ) + FunctionNaming:SkontoFragment.kt$@Composable private fun SkontoSection( colors: SkontoSectionColors, amount: SkontoData.Amount, dueDate: LocalDate, infoPaymentInDays: Int, infoDiscountValue: BigDecimal, onActiveChange: (Boolean) -> Unit, onSkontoAmountChange: (BigDecimal) -> Unit, onDueDateChanged: (LocalDate) -> Unit, onInfoBannerClicked: () -> Unit, edgeCase: SkontoFragmentContract.SkontoEdgeCase?, modifier: Modifier = Modifier, isActive: Boolean, ) + FunctionNaming:SkontoFragment.kt$@Composable private fun TopAppBar( onBackClicked: () -> Unit, modifier: Modifier = Modifier, isBottomNavigationBarEnabled: Boolean, colors: GiniTopBarColors, ) + FunctionNaming:SkontoFragment.kt$@Composable private fun WithoutSkontoSection( colors: WithoutSkontoSectionColors, amount: SkontoData.Amount, modifier: Modifier = Modifier, onFullAmountChange: (BigDecimal) -> Unit, isActive: Boolean, ) + FunctionNaming:SkontoFragment.kt$@Composable private fun YourInvoiceScanSection( modifier: Modifier = Modifier, colorScheme: SkontoInvoiceScanSectionColors, ) LongMethod:Configuration.kt$internal fun GiniCapture.Builder.applyConfiguration(configuration: CaptureConfiguration): GiniCapture.Builder LongMethod:SkontoFragment.kt$@Composable private fun FooterSection( totalAmount: SkontoData.Amount, savedAmount: SkontoData.Amount, discountValue: BigDecimal, colors: SkontoFooterSectionColors, isBottomNavigationBarEnabled: Boolean, isSkontoSectionActive: Boolean, onBackClicked: () -> Unit, onProceedClicked: () -> Unit, modifier: Modifier = Modifier, customBottomNavBarAdapter: InjectedViewAdapterInstance<SkontoNavigationBarBottomAdapter>?, ) LongMethod:SkontoFragment.kt$@Composable private fun ScreenReadyState( onBackClicked: () -> Unit, onProceedClicked: () -> Unit, state: SkontoFragmentContract.State.Ready, onDiscountSectionActiveChange: (Boolean) -> Unit, onDiscountAmountChange: (BigDecimal) -> Unit, onDueDateChanged: (LocalDate) -> Unit, onFullAmountChange: (BigDecimal) -> Unit, isBottomNavigationBarEnabled: Boolean, customBottomNavBarAdapter: InjectedViewAdapterInstance<SkontoNavigationBarBottomAdapter>?, modifier: Modifier = Modifier, screenColorScheme: SkontoScreenColors = SkontoScreenColors.colors(), onInfoBannerClicked: () -> Unit, onInfoDialogDismissed: () -> Unit, ) @@ -44,7 +58,6 @@ MaxLineLength:BigDecimalExtensions.kt$internal MaxLineLength:CaptureFlowActivity.kt$CaptureFlowActivity$* Entry point for Screen API. It exists for the purpose of communication between Capture SDK's Screen API and Return Assistant. MaxLineLength:CaptureFlowFragment.kt$CaptureFlowFragment$// To be the first to handle back button pressed events we need to set this fragment as the primary navigation fragment - MaxLineLength:Configuration.kt$CaptureConfiguration$* MaxLineLength:Configuration.kt$CaptureConfiguration$* Enable and configure the document import feature or disable it by passing in [DocumentImportEnabledFileTypes.NONE]. MaxLineLength:DigitalInvoice.kt$DigitalInvoice$private MaxLineLength:DigitalInvoice.kt$DigitalInvoice$selectableLineItems.map { sli -> if (sli.lineItem.id == selectableLineItem.lineItem.id) selectableLineItem else sli } @@ -135,10 +148,10 @@ SerialVersionUIDInSerializableClass:SkontoData.kt$SkontoData : Serializable SerialVersionUIDInSerializableClass:SkontoData.kt$SkontoData$Amount : Serializable SerialVersionUIDInSerializableClass:SkontoData.kt$SkontoData$SkontoPaymentMethod : Serializable - SwallowedException:CaptureFlowFragment.kt$CaptureFlowFragment$catch (e: Exception) { finishWithResult(result) } - SwallowedException:CaptureFlowFragment.kt$CaptureFlowFragment$catch (notUsed: DigitalInvoiceException) { tryShowingSkontoScreen(result) return } - SwallowedException:DigitalInvoiceAddon.kt$DigitalInvoiceAddon.Companion$catch (e: Exception) { Pair(null, null) } - SwallowedException:LineItem.kt$LineItem$catch (e: Exception) { Triple(BigDecimal.ZERO, "", null) } + SwallowedException:CaptureFlowFragment.kt$CaptureFlowFragment$e: Exception + SwallowedException:CaptureFlowFragment.kt$CaptureFlowFragment$notUsed: DigitalInvoiceException + SwallowedException:DigitalInvoiceAddon.kt$DigitalInvoiceAddon.Companion$e: Exception + SwallowedException:LineItem.kt$LineItem$e: Exception ThrowsCount:SkontoDataExtractor.kt$SkontoDataExtractor.Companion$fun extractSkontoData( extractions: Map<String, GiniCaptureSpecificExtraction>, compoundExtractions: Map<String, GiniCaptureCompoundExtraction>, ): SkontoData TooGenericExceptionCaught:CaptureFlowFragment.kt$CaptureFlowFragment$e: Exception TooGenericExceptionCaught:DigitalInvoiceAddon.kt$DigitalInvoiceAddon.Companion$e: Exception @@ -153,7 +166,7 @@ TooManyFunctions:DigitalInvoiceFragment.kt$DigitalInvoiceFragment : FragmentViewLineItemsAdapterListener TooManyFunctions:DigitalInvoiceOnboardingFragment.kt$DigitalInvoiceOnboardingFragment : FragmentView TooManyFunctions:DigitalInvoiceScreenPresenter.kt$DigitalInvoiceScreenPresenter : Presenter - TooManyFunctions:GiniBank.kt$GiniBank$GiniBank + TooManyFunctions:GiniBank.kt$GiniBank TooManyFunctions:LineItemDetailsScreenContract.kt$LineItemDetailsScreenContract$View : GiniCaptureBaseView TooManyFunctions:LineItemDetailsScreenPresenter.kt$LineItemDetailsScreenPresenter : Presenter TooManyFunctions:ReturnReasonsDialog.kt$ReturnReasonDialog : BottomSheetDialogFragment @@ -161,11 +174,13 @@ TooManyFunctions:SkontoFragmentViewModel.kt$SkontoFragmentViewModel : ViewModel TopLevelPropertyNaming:PaymentRequestIntent.kt$internal const val Scheme = "ginipay" // It has to match the scheme in query tag in manifest TopLevelPropertyNaming:PaymentRequestIntent.kt$private const val PaymentPath = "payment" - UnusedPrivateMember:DigitalInvoiceFragment.kt$private const val TAG_WHAT_IS_THIS_DIALOG = "TAG_WHAT_IS_THIS_DIALOG" - UnusedPrivateMember:SkontoDataExtractor.kt$SkontoDataExtractor.Companion$val skontoAmountDiscounted = skontoDiscountData.extractDataByKeys( "skontoAmountDiscounted", "skontoAmountDiscountedCalculated" ) UnusedPrivateMember:SkontoFragment.kt$@Composable @Preview private fun ScreenReadyStatePreviewLight() UnusedPrivateMember:SkontoFragment.kt$@Composable @Preview(uiMode = UI_MODE_NIGHT_YES) private fun ScreenReadyStatePreviewDark() UnusedPrivateMember:SkontoFragment.kt$@Composable private fun YourInvoiceScanSection( modifier: Modifier = Modifier, colorScheme: SkontoInvoiceScanSectionColors, ) + UnusedPrivateProperty:DigitalInvoiceFragment.kt$private const val TAG_WHAT_IS_THIS_DIALOG = "TAG_WHAT_IS_THIS_DIALOG" + UnusedPrivateProperty:SkontoDataExtractor.kt$SkontoDataExtractor.Companion$val skontoAmountDiscounted = skontoDiscountData.extractDataByKeys( "skontoAmountDiscounted", "skontoAmountDiscountedCalculated" ) + UseCheckOrError:AutoClearedValue.kt$AutoClearedValue$throw IllegalStateException( "should never call auto-cleared-value get when it might not be available" ) + UseCheckOrError:LineItemsAdapter.kt$ViewType.Companion$throw IllegalStateException("Unknow adapter view type id: $viewTypeId") UtilityClassWithPublicConstructor:LineItemsValidator.kt$LineItemsValidator UtilityClassWithPublicConstructor:SkontoDataExtractor.kt$SkontoDataExtractor WildcardImport:CoroutineContinuationHelper.kt$import kotlinx.coroutines.* diff --git a/capture-sdk/sdk/detekt-baseline.xml b/capture-sdk/sdk/detekt-baseline.xml index 3c638b802..9662696b2 100644 --- a/capture-sdk/sdk/detekt-baseline.xml +++ b/capture-sdk/sdk/detekt-baseline.xml @@ -2,12 +2,13 @@ - ComplexMethod:DefaultPages.kt$DefaultPages.Companion$ @JvmStatic fun asArrayList(isMultiPageEnabled: Boolean, isQRCodeScanningEnabled: Boolean): ArrayList<OnboardingPage> - ComplexMethod:ErrorType.kt$ErrorType.Companion$@JvmStatic fun typeFromError(error: Error): ErrorType - ComplexMethod:TypographyToTextStyleBridge.kt$ internal fun TypedArray.getFontFamilyOrNull(index: Int): FontFamilyWithWeight? - ComplexMethod:TypographyToTextStyleBridge.kt$@Composable fun textStyleFromTextAppearance( @StyleRes id: Int, density: Density = Density(LocalContext.current), setTextColors: Boolean = true ): TextStyle + CyclomaticComplexMethod:DefaultPages.kt$DefaultPages.Companion$@JvmStatic fun asArrayList(isMultiPageEnabled: Boolean, isQRCodeScanningEnabled: Boolean): ArrayList<OnboardingPage> + CyclomaticComplexMethod:ErrorType.kt$ErrorType.Companion$@JvmStatic fun typeFromError(error: Error): ErrorType + CyclomaticComplexMethod:TypographyToTextStyleBridge.kt$@Composable fun textStyleFromTextAppearance( @StyleRes id: Int, density: Density = Density(LocalContext.current), setTextColors: Boolean = true ): TextStyle + CyclomaticComplexMethod:TypographyToTextStyleBridge.kt$internal fun TypedArray.getFontFamilyOrNull(index: Int): FontFamilyWithWeight? EmptyCatchBlock:DeviceInfo.kt$DeviceInfo.CachedInfo${ } EmptyDefaultConstructor:CameraXController.kt$CameraLifecycle$() + EmptyElseBlock:IntervalClickListener.kt$IntervalClickListener$if (view == null) return EmptyFunctionBlock:CameraXController.kt$CameraXController.<no name provided>${} EmptyFunctionBlock:CustomLoadingIndicatorAdapter.kt$DefaultLoadingIndicatorAdapter${} EmptyFunctionBlock:OnButtonLoadingIndicatorAdapter.kt$DefaultOnButtonLoadingIndicatorAdapter${} @@ -15,9 +16,34 @@ EmptyFunctionBlock:PreviewPagesAdapter.kt$PreviewPagesAdapter.<no name provided>${ } ForbiddenComment:TypographyToTextStyleBridge.kt$// FIXME: Normally we'd use TextUnit.Unspecified, ForbiddenComment:TypographyToTextStyleBridge.kt$// TODO: Compose does not expose a FontFamily for all strings yet + FunctionNaming:GiniAmountTextInput.kt$@Composable fun GiniAmountTextInput( amount: BigDecimal, currencyCode: String, label: String, modifier: Modifier = Modifier, onValueChange: (BigDecimal) -> Unit, trailingContent: @Composable () -> Unit = {}, enabled: Boolean = true, isError: Boolean = false, decimalFormatter: DecimalFormatter = DecimalFormatter(), colors: GiniTextInputColors = GiniTextInputColors.colors(), ) + FunctionNaming:GiniAmountTextInput.kt$@Composable private fun GiniTextInputPreview() + FunctionNaming:GiniAmountTextInput.kt$@Preview( showBackground = true, uiMode = Configuration.UI_MODE_NIGHT_YES ) @Composable private fun GiniTextInputPreviewDark() + FunctionNaming:GiniAmountTextInput.kt$@Preview(showBackground = true) @Composable private fun GiniTextInputPreviewLight() + FunctionNaming:GiniButton.kt$@Composable fun GiniButton( onClick: () -> Unit, modifier: Modifier = Modifier, giniButtonColors: GiniButtonColors = GiniButtonColors.colors(), content: @Composable () -> Unit, ) + FunctionNaming:GiniButton.kt$@Composable fun GiniButton( text: String, onClick: () -> Unit, modifier: Modifier = Modifier, giniButtonColors: GiniButtonColors = GiniButtonColors(), ) + FunctionNaming:GiniButton.kt$@Preview @Composable private fun GiniContentButtonPreview() + FunctionNaming:GiniButton.kt$@Preview @Composable private fun GiniTextButtonPreview() + FunctionNaming:GiniDatePickerDialog.kt$@Composable fun GiniDatePickerDialog( onDismissRequest: () -> Unit, onSaved: (LocalDate) -> Unit, modifier: Modifier = Modifier, date: LocalDate = LocalDate.now(), selectableDates: SelectableDates = DatePickerDefaults.AllDates, colors: GiniDatePickerDialogColors = GiniDatePickerDialogColors.colors() ) + FunctionNaming:GiniDatePickerDialog.kt$@Composable private fun DatePickerDialogPreview() + FunctionNaming:GiniDatePickerDialog.kt$@Preview @Composable private fun DatePickerDialogPreviewLight() + FunctionNaming:GiniDatePickerDialog.kt$@Preview(uiMode = UI_MODE_NIGHT_YES) @Composable private fun DatePickerDialogPreviewDark() + FunctionNaming:GiniSwitch.kt$@Composable fun GiniSwitch( modifier: Modifier = Modifier, checked: Boolean, onCheckedChange: (Boolean) -> Unit, giniSwitchColors: GiniSwitchColors = GiniSwitchColors.colors(), ) + FunctionNaming:GiniSwitch.kt$@Preview(showBackground = true) @Composable private fun GiniSwitchPreview() + FunctionNaming:GiniTextInput.kt$@Composable fun GiniTextInput( text: String, label: @Composable () -> Unit, onValueChange: (String) -> Unit, modifier: Modifier = Modifier, trailingContent: @Composable () -> Unit = {}, enabled: Boolean = true, isError: Boolean = false, readOnly: Boolean = false, keyboardOptions: KeyboardOptions = KeyboardOptions.Default, colors: GiniTextInputColors = GiniTextInputColors.colors(), visualTransformation: VisualTransformation = VisualTransformation.None, interactionSource: MutableInteractionSource = remember { MutableInteractionSource() }, ) + FunctionNaming:GiniTextInput.kt$@Composable fun GiniTextInput( text: String, label: String, modifier: Modifier = Modifier, onValueChange: (String) -> Unit, trailingContent: @Composable () -> Unit = {}, enabled: Boolean = true, isError: Boolean = false, readOnly: Boolean = false, keyboardOptions: KeyboardOptions = KeyboardOptions.Default, colors: GiniTextInputColors = GiniTextInputColors.colors(), visualTransformation: VisualTransformation = VisualTransformation.None, interactionSource: MutableInteractionSource = remember { MutableInteractionSource() }, ) + FunctionNaming:GiniTextInput.kt$@Composable private fun GiniTextInputPreview() + FunctionNaming:GiniTextInput.kt$@Preview( showBackground = true, uiMode = Configuration.UI_MODE_NIGHT_YES ) @Composable private fun GiniTextInputPreviewDark() + FunctionNaming:GiniTextInput.kt$@Preview(showBackground = true) @Composable private fun GiniTextInputPreviewLight() + FunctionNaming:GiniTheme.kt$@Composable fun GiniTheme( content: @Composable () -> Unit ) + FunctionNaming:GiniTopBar.kt$@Composable fun GiniTopBar( title: @Composable () -> Unit, navigationIcon: @Composable () -> Unit, actions: @Composable RowScope.() -> Unit, modifier: Modifier = Modifier, colors: GiniTopBarColors = GiniTopBarColors.colors(), ) + FunctionNaming:GiniTopBar.kt$@Composable fun GiniTopBar( title: String, modifier: Modifier = Modifier, navigationIcon: @Composable () -> Unit = {}, actions: @Composable RowScope.() -> Unit = {}, colors: GiniTopBarColors = GiniTopBarColors.colors(), ) + FunctionNaming:GiniTopBar.kt$@Composable private fun GiniTopBarPreview() + FunctionNaming:GiniTopBar.kt$@Preview @Composable private fun GiniTopBarPreviewLight() + FunctionNaming:GiniTopBar.kt$@Preview(uiMode = Configuration.UI_MODE_NIGHT_YES) @Composable private fun GiniTopBarPreviewDark() LongMethod:CameraXController.kt$CameraXController$override fun open(): CompletableFuture<Void> - LongMethod:GiniColorPalette.kt$ internal fun giniDarkColorScheme( giniColorPrimitives: GiniColorPrimitives = GiniColorPrimitives() ) - LongMethod:GiniColorPalette.kt$ internal fun giniLightColorScheme( giniColorPrimitives: GiniColorPrimitives = GiniColorPrimitives() ) + LongMethod:GiniColorPalette.kt$internal fun giniDarkColorScheme( giniColorPrimitives: GiniColorPrimitives = GiniColorPrimitives() ) + LongMethod:GiniColorPalette.kt$internal fun giniLightColorScheme( giniColorPrimitives: GiniColorPrimitives = GiniColorPrimitives() ) LongMethod:GiniDatePickerDialog.kt$@Composable fun GiniDatePickerDialog( onDismissRequest: () -> Unit, onSaved: (LocalDate) -> Unit, modifier: Modifier = Modifier, date: LocalDate = LocalDate.now(), selectableDates: SelectableDates = DatePickerDefaults.AllDates, colors: GiniDatePickerDialogColors = GiniDatePickerDialogColors.colors() ) LongMethod:TypographyToTextStyleBridge.kt$@Composable fun textStyleFromTextAppearance( @StyleRes id: Int, density: Density = Density(LocalContext.current), setTextColors: Boolean = true ): TextStyle LongParameterList:GiniAmountTextInput.kt$( amount: BigDecimal, currencyCode: String, label: String, modifier: Modifier = Modifier, onValueChange: (BigDecimal) -> Unit, trailingContent: @Composable () -> Unit = {}, enabled: Boolean = true, isError: Boolean = false, decimalFormatter: DecimalFormatter = DecimalFormatter(), colors: GiniTextInputColors = GiniTextInputColors.colors(), ) @@ -119,7 +145,6 @@ MagicNumber:TypographyToTextStyleBridge.kt$23 MagicNumber:TypographyToTextStyleBridge.kt$249 MagicNumber:TypographyToTextStyleBridge.kt$250 - MagicNumber:TypographyToTextStyleBridge.kt$3 MagicNumber:TypographyToTextStyleBridge.kt$349 MagicNumber:TypographyToTextStyleBridge.kt$350 MagicNumber:TypographyToTextStyleBridge.kt$449 @@ -162,7 +187,7 @@ MaxLineLength:IntervalToolbarMenuItemIntervalClickListener.kt$IntervalToolbarMenuItemIntervalClickListener$class MaxLineLength:TypographyToTextStyleBridge.kt$fontFeatureSettings = a.getString(R.styleable.ComposeThemeAdapterTextAppearance_android_fontFeatureSettings) MaxLineLength:UserAnalytics.kt$UserAnalytics$(eventTracker as? BufferedUserAnalyticsEventTracker)?.setPlatformTokens(*tokens, networkRequestsManager = networkRequestsManager) - NestedBlockDepth:TypographyToTextStyleBridge.kt$ internal fun TypedArray.getFontFamilyOrNull(index: Int): FontFamilyWithWeight? + NestedBlockDepth:TypographyToTextStyleBridge.kt$internal fun TypedArray.getFontFamilyOrNull(index: Int): FontFamilyWithWeight? NewLineAtEndOfFile:Amount.kt$net.gini.android.capture.Amount.kt NewLineAtEndOfFile:AmountCurrency.kt$net.gini.android.capture.AmountCurrency.kt NewLineAtEndOfFile:AmplitudeUserAnalyticsEventTracker.kt$net.gini.android.capture.tracking.useranalytics.tracker.AmplitudeUserAnalyticsEventTracker.kt @@ -241,11 +266,10 @@ ReturnCount:ErrorType.kt$ErrorType.Companion$private fun isInvalidUserError(error: Error): Boolean ReturnCount:GiniCaptureFragment.kt$CaptureFragmentFactory$override fun instantiate(classLoader: ClassLoader, className: String): Fragment ReturnCount:SnappedItemChangeRecyclerViewListener.kt$SnappedItemChangeRecyclerViewListener$override fun onScrollStateChanged(recyclerView: RecyclerView, newState: Int) - SwallowedException:DeviceInfo.kt$DeviceInfo.CachedInfo$catch (e: Exception) { // Failed to get network operator name from network } - SwallowedException:DeviceInfo.kt$DeviceInfo.CachedInfo$catch (e: Exception) { } - SwallowedException:DeviceInfo.kt$DeviceInfo.CachedInfo$catch (e: PackageManager.NameNotFoundException) { } - SwallowedException:ErrorType.kt$ErrorType.Companion$catch (e: Exception) { false } - SwallowedException:IBANRecognizerImpl.kt$IBANRecognizerImpl$catch (e: IBANValidator.IllegalIBANException) { false } + SwallowedException:DeviceInfo.kt$DeviceInfo.CachedInfo$e: Exception + SwallowedException:DeviceInfo.kt$DeviceInfo.CachedInfo$e: PackageManager.NameNotFoundException + SwallowedException:ErrorType.kt$ErrorType.Companion$e: Exception + SwallowedException:IBANRecognizerImpl.kt$IBANRecognizerImpl$e: IBANValidator.IllegalIBANException ThrowsCount:Extensions.kt$@Throws(CameraException::class) private fun cropByteArray(data: ByteArray, cropRect: Rect?): ByteArray ThrowsCount:IBANValidator.kt$IBANValidator$@Throws(IllegalIBANException::class) private fun validateLength(iban: String) TooGenericExceptionCaught:CameraXController.kt$CameraXController$e: Exception @@ -256,11 +280,8 @@ TooManyFunctions:FileChooserFragment.kt$FileChooserFragment : BottomSheetDialogFragment TooManyFunctions:GiniCaptureFragment.kt$GiniCaptureFragment : FragmentCameraFragmentListenerAnalysisFragmentListenerEnterManuallyButtonListenerCancelListener TooManyFunctions:HelpFragment.kt$HelpFragment : Fragment - UnnecessaryAbstractClass:AnalyticsKeyPairProperty.kt$AnalyticsKeyPairProperty - UnusedPrivateMember:AmplitudeUserAnalyticsEventTracker.kt$AmplitudeUserAnalyticsEventTracker$val version = BuildConfig.VERSION_NAME - UnusedPrivateMember:DecimalInputVisualTransformation.kt$DecimalInputVisualTransformation.CustomOffsetMapping$val thousandSeparatorCount = formatted.count { it == formattingSymbols.groupingSeparator } - UnusedPrivateMember:DeviceInfo.kt$DeviceInfo$private val LOG = LoggerFactory.getLogger(DeviceInfo::class.java) - UnusedPrivateMember:ErrorFragmentImpl.kt$ErrorFragmentImpl$savedInstanceState: Bundle? + UnusedParameter:ErrorFragmentImpl.kt$ErrorFragmentImpl$savedInstanceState: Bundle? + UnusedParameter:TypographyToTextStyleBridge.kt$setTextColors: Boolean = true UnusedPrivateMember:GiniAmountTextInput.kt$@Preview( showBackground = true, uiMode = Configuration.UI_MODE_NIGHT_YES ) @Composable private fun GiniTextInputPreviewDark() UnusedPrivateMember:GiniAmountTextInput.kt$@Preview(showBackground = true) @Composable private fun GiniTextInputPreviewLight() UnusedPrivateMember:GiniButton.kt$@Preview @Composable private fun GiniContentButtonPreview() @@ -272,7 +293,13 @@ UnusedPrivateMember:GiniTextInput.kt$@Preview(showBackground = true) @Composable private fun GiniTextInputPreviewLight() UnusedPrivateMember:GiniTopBar.kt$@Preview @Composable private fun GiniTopBarPreviewLight() UnusedPrivateMember:GiniTopBar.kt$@Preview(uiMode = Configuration.UI_MODE_NIGHT_YES) @Composable private fun GiniTopBarPreviewDark() - UnusedPrivateMember:TypographyToTextStyleBridge.kt$setTextColors: Boolean = true + UnusedPrivateProperty:AmplitudeUserAnalyticsEventTracker.kt$AmplitudeUserAnalyticsEventTracker$val version = BuildConfig.VERSION_NAME + UnusedPrivateProperty:DecimalInputVisualTransformation.kt$DecimalInputVisualTransformation.CustomOffsetMapping$val thousandSeparatorCount = formatted.count { it == formattingSymbols.groupingSeparator } + UnusedPrivateProperty:DeviceInfo.kt$DeviceInfo$private val LOG = LoggerFactory.getLogger(DeviceInfo::class.java) + UseCheckOrError:AutoClearedValue.kt$AutoClearedValue$throw IllegalStateException( "should never call auto-cleared-value get when it might not be available" ) + UseCheckOrError:UserAnalytics.kt$UserAnalytics$throw IllegalStateException( "You need to initialize analytics by calling `UserAnalytics.initialize(...)`" ) + UseRequire:IBANRecognizerImpl.kt$IBANRecognizerImpl$throw IllegalArgumentException("Image height is 0") + UseRequire:IBANRecognizerImpl.kt$IBANRecognizerImpl$throw IllegalArgumentException("Image width is 0") VariableNaming:AmplitudeUserAnalyticsEventTracker.kt$AmplitudeUserAnalyticsEventTracker$private val LOG = LoggerFactory.getLogger(AmplitudeUserAnalyticsEventTracker::class.java) VariableNaming:BufferedUserAnalyticsEventTracker.kt$BufferedUserAnalyticsEventTracker$private val LOG = LoggerFactory.getLogger(BufferedUserAnalyticsEventTracker::class.java) VariableNaming:DeviceInfo.kt$DeviceInfo$private val LOG = LoggerFactory.getLogger(DeviceInfo::class.java) diff --git a/config/detekt/detekt.yml b/config/detekt/detekt.yml new file mode 100644 index 000000000..9b4a4ed99 --- /dev/null +++ b/config/detekt/detekt.yml @@ -0,0 +1,788 @@ +build: + maxIssues: 0 + excludeCorrectable: false + weights: + # complexity: 2 + # LongParameterList: 1 + # style: 1 + # comments: 1 + +config: + validation: true + warningsAsErrors: false + checkExhaustiveness: false + # when writing own rules with new properties, exclude the property path e.g.: 'my_rule_set,.*>.*>[my_property]' + excludes: '' + +processors: + active: true + exclude: + - 'DetektProgressListener' + # - 'KtFileCountProcessor' + # - 'PackageCountProcessor' + # - 'ClassCountProcessor' + # - 'FunctionCountProcessor' + # - 'PropertyCountProcessor' + # - 'ProjectComplexityProcessor' + # - 'ProjectCognitiveComplexityProcessor' + # - 'ProjectLLOCProcessor' + # - 'ProjectCLOCProcessor' + # - 'ProjectLOCProcessor' + # - 'ProjectSLOCProcessor' + # - 'LicenseHeaderLoaderExtension' + +console-reports: + active: true + exclude: + - 'ProjectStatisticsReport' + - 'ComplexityReport' + - 'NotificationReport' + - 'FindingsReport' + - 'FileBasedFindingsReport' + # - 'LiteFindingsReport' + +output-reports: + active: true + exclude: + # - 'TxtOutputReport' + # - 'XmlOutputReport' + # - 'HtmlOutputReport' + # - 'MdOutputReport' + # - 'SarifOutputReport' + +comments: + active: true + AbsentOrWrongFileLicense: + active: false + licenseTemplateFile: 'license.template' + licenseTemplateIsRegex: false + CommentOverPrivateFunction: + active: false + CommentOverPrivateProperty: + active: false + DeprecatedBlockTag: + active: false + EndOfSentenceFormat: + active: false + endOfSentenceFormat: '([.?!][ \t\n\r\f<])|([.?!:]$)' + KDocReferencesNonPublicProperty: + active: false + excludes: [ '**/test/**', '**/androidTest/**', '**/commonTest/**', '**/jvmTest/**', '**/androidUnitTest/**', '**/androidInstrumentedTest/**', '**/jsTest/**', '**/iosTest/**' ] + OutdatedDocumentation: + active: false + matchTypeParameters: true + matchDeclarationsOrder: true + allowParamOnConstructorProperties: false + UndocumentedPublicClass: + active: false + excludes: [ '**/test/**', '**/androidTest/**', '**/commonTest/**', '**/jvmTest/**', '**/androidUnitTest/**', '**/androidInstrumentedTest/**', '**/jsTest/**', '**/iosTest/**' ] + searchInNestedClass: true + searchInInnerClass: true + searchInInnerObject: true + searchInInnerInterface: true + searchInProtectedClass: false + UndocumentedPublicFunction: + active: false + excludes: [ '**/test/**', '**/androidTest/**', '**/commonTest/**', '**/jvmTest/**', '**/androidUnitTest/**', '**/androidInstrumentedTest/**', '**/jsTest/**', '**/iosTest/**' ] + searchProtectedFunction: false + UndocumentedPublicProperty: + active: false + excludes: [ '**/test/**', '**/androidTest/**', '**/commonTest/**', '**/jvmTest/**', '**/androidUnitTest/**', '**/androidInstrumentedTest/**', '**/jsTest/**', '**/iosTest/**' ] + searchProtectedProperty: false + +complexity: + active: true + CognitiveComplexMethod: + active: false + threshold: 15 + ComplexCondition: + active: true + threshold: 4 + ComplexInterface: + active: false + threshold: 10 + includeStaticDeclarations: false + includePrivateDeclarations: false + ignoreOverloaded: false + CyclomaticComplexMethod: + active: true + threshold: 15 + ignoreSingleWhenExpression: false + ignoreSimpleWhenEntries: false + ignoreNestingFunctions: false + nestingFunctions: + - 'also' + - 'apply' + - 'forEach' + - 'isNotNull' + - 'ifNull' + - 'let' + - 'run' + - 'use' + - 'with' + LabeledExpression: + active: false + ignoredLabels: [ ] + LargeClass: + active: true + threshold: 600 + LongMethod: + active: true + threshold: 60 + LongParameterList: + active: true + functionThreshold: 6 + constructorThreshold: 7 + ignoreDefaultParameters: true + ignoreDataClasses: true + ignoreAnnotatedParameter: [ ] + MethodOverloading: + active: false + threshold: 6 + NamedArguments: + active: false + threshold: 3 + ignoreArgumentsMatchingNames: false + NestedBlockDepth: + active: true + threshold: 4 + NestedScopeFunctions: + active: false + threshold: 1 + functions: + - 'kotlin.apply' + - 'kotlin.run' + - 'kotlin.with' + - 'kotlin.let' + - 'kotlin.also' + ReplaceSafeCallChainWithRun: + active: false + StringLiteralDuplication: + active: false + excludes: [ '**/test/**', '**/androidTest/**', '**/commonTest/**', '**/jvmTest/**', '**/androidUnitTest/**', '**/androidInstrumentedTest/**', '**/jsTest/**', '**/iosTest/**' ] + threshold: 3 + ignoreAnnotation: true + excludeStringsWithLessThan5Characters: true + ignoreStringsRegex: '$^' + TooManyFunctions: + active: true + excludes: [ '**/test/**', '**/androidTest/**', '**/commonTest/**', '**/jvmTest/**', '**/androidUnitTest/**', '**/androidInstrumentedTest/**', '**/jsTest/**', '**/iosTest/**' ] + thresholdInFiles: 11 + thresholdInClasses: 11 + thresholdInInterfaces: 11 + thresholdInObjects: 11 + thresholdInEnums: 11 + ignoreDeprecated: false + ignorePrivate: false + ignoreOverridden: false + ignoreAnnotatedFunctions: [ 'Preview' ] + +coroutines: + active: true + GlobalCoroutineUsage: + active: false + InjectDispatcher: + active: true + dispatcherNames: + - 'IO' + - 'Default' + - 'Unconfined' + RedundantSuspendModifier: + active: true + SleepInsteadOfDelay: + active: true + SuspendFunSwallowedCancellation: + active: false + SuspendFunWithCoroutineScopeReceiver: + active: false + SuspendFunWithFlowReturnType: + active: true + +empty-blocks: + active: true + EmptyCatchBlock: + active: true + allowedExceptionNameRegex: '_|(ignore|expected).*' + EmptyClassBlock: + active: true + EmptyDefaultConstructor: + active: true + EmptyDoWhileBlock: + active: true + EmptyElseBlock: + active: true + EmptyFinallyBlock: + active: true + EmptyForBlock: + active: true + EmptyFunctionBlock: + active: true + ignoreOverridden: false + EmptyIfBlock: + active: true + EmptyInitBlock: + active: true + EmptyKtFile: + active: true + EmptySecondaryConstructor: + active: true + EmptyTryBlock: + active: true + EmptyWhenBlock: + active: true + EmptyWhileBlock: + active: true + +exceptions: + active: true + ExceptionRaisedInUnexpectedLocation: + active: true + methodNames: + - 'equals' + - 'finalize' + - 'hashCode' + - 'toString' + InstanceOfCheckForException: + active: true + excludes: [ '**/test/**', '**/androidTest/**', '**/commonTest/**', '**/jvmTest/**', '**/androidUnitTest/**', '**/androidInstrumentedTest/**', '**/jsTest/**', '**/iosTest/**' ] + NotImplementedDeclaration: + active: false + ObjectExtendsThrowable: + active: false + PrintStackTrace: + active: true + RethrowCaughtException: + active: true + ReturnFromFinally: + active: true + ignoreLabeled: false + SwallowedException: + active: true + ignoredExceptionTypes: + - 'InterruptedException' + - 'MalformedURLException' + - 'NumberFormatException' + - 'ParseException' + allowedExceptionNameRegex: '_|(ignore|expected).*' + ThrowingExceptionFromFinally: + active: true + ThrowingExceptionInMain: + active: false + ThrowingExceptionsWithoutMessageOrCause: + active: true + excludes: [ '**/test/**', '**/androidTest/**', '**/commonTest/**', '**/jvmTest/**', '**/androidUnitTest/**', '**/androidInstrumentedTest/**', '**/jsTest/**', '**/iosTest/**' ] + exceptions: + - 'ArrayIndexOutOfBoundsException' + - 'Exception' + - 'IllegalArgumentException' + - 'IllegalMonitorStateException' + - 'IllegalStateException' + - 'IndexOutOfBoundsException' + - 'NullPointerException' + - 'RuntimeException' + - 'Throwable' + ThrowingNewInstanceOfSameException: + active: true + TooGenericExceptionCaught: + active: true + excludes: [ '**/test/**', '**/androidTest/**', '**/commonTest/**', '**/jvmTest/**', '**/androidUnitTest/**', '**/androidInstrumentedTest/**', '**/jsTest/**', '**/iosTest/**' ] + exceptionNames: + - 'ArrayIndexOutOfBoundsException' + - 'Error' + - 'Exception' + - 'IllegalMonitorStateException' + - 'IndexOutOfBoundsException' + - 'NullPointerException' + - 'RuntimeException' + - 'Throwable' + allowedExceptionNameRegex: '_|(ignore|expected).*' + TooGenericExceptionThrown: + active: true + exceptionNames: + - 'Error' + - 'Exception' + - 'RuntimeException' + - 'Throwable' + +naming: + active: true + BooleanPropertyNaming: + active: false + allowedPattern: '^(is|has|are)' + ClassNaming: + active: true + classPattern: '[A-Z][a-zA-Z0-9]*' + ConstructorParameterNaming: + active: true + parameterPattern: '[a-z][A-Za-z0-9]*' + privateParameterPattern: '[a-z][A-Za-z0-9]*' + excludeClassPattern: '$^' + EnumNaming: + active: true + enumEntryPattern: '[A-Z][_a-zA-Z0-9]*' + ForbiddenClassName: + active: false + forbiddenName: [ ] + FunctionMaxLength: + active: false + maximumFunctionNameLength: 30 + FunctionMinLength: + active: false + minimumFunctionNameLength: 3 + FunctionNaming: + active: true + excludes: [ '**/test/**', '**/androidTest/**', '**/commonTest/**', '**/jvmTest/**', '**/androidUnitTest/**', '**/androidInstrumentedTest/**', '**/jsTest/**', '**/iosTest/**' ] + functionPattern: '[a-z][a-zA-Z0-9]*' + excludeClassPattern: '$^' + ignoreAnnotated: [ 'Composable' ] + FunctionParameterNaming: + active: true + parameterPattern: '[a-z][A-Za-z0-9]*' + excludeClassPattern: '$^' + InvalidPackageDeclaration: + active: true + rootPackage: '' + requireRootInDeclaration: false + LambdaParameterNaming: + active: false + parameterPattern: '[a-z][A-Za-z0-9]*|_' + MatchingDeclarationName: + active: true + mustBeFirst: true + MemberNameEqualsClassName: + active: true + ignoreOverridden: true + NoNameShadowing: + active: true + NonBooleanPropertyPrefixedWithIs: + active: false + ObjectPropertyNaming: + active: true + constantPattern: '[A-Za-z][_A-Za-z0-9]*' + propertyPattern: '[A-Za-z][_A-Za-z0-9]*' + privatePropertyPattern: '(_)?[A-Za-z][_A-Za-z0-9]*' + PackageNaming: + active: true + packagePattern: '[a-z]+(\.[a-z][A-Za-z0-9]*)*' + TopLevelPropertyNaming: + active: true + constantPattern: '[A-Z][_A-Z0-9]*' + propertyPattern: '[A-Za-z][_A-Za-z0-9]*' + privatePropertyPattern: '_?[A-Za-z][_A-Za-z0-9]*' + ignoreAnnotated: [ 'Composable' ] + VariableMaxLength: + active: false + maximumVariableNameLength: 64 + VariableMinLength: + active: false + minimumVariableNameLength: 1 + VariableNaming: + active: true + variablePattern: '[a-z][A-Za-z0-9]*' + privateVariablePattern: '(_)?[a-z][A-Za-z0-9]*' + excludeClassPattern: '$^' + +performance: + active: true + ArrayPrimitive: + active: true + CouldBeSequence: + active: false + threshold: 3 + ForEachOnRange: + active: true + excludes: [ '**/test/**', '**/androidTest/**', '**/commonTest/**', '**/jvmTest/**', '**/androidUnitTest/**', '**/androidInstrumentedTest/**', '**/jsTest/**', '**/iosTest/**' ] + SpreadOperator: + active: true + excludes: [ '**/test/**', '**/androidTest/**', '**/commonTest/**', '**/jvmTest/**', '**/androidUnitTest/**', '**/androidInstrumentedTest/**', '**/jsTest/**', '**/iosTest/**' ] + UnnecessaryPartOfBinaryExpression: + active: false + UnnecessaryTemporaryInstantiation: + active: true + +potential-bugs: + active: true + AvoidReferentialEquality: + active: true + forbiddenTypePatterns: + - 'kotlin.String' + CastNullableToNonNullableType: + active: false + CastToNullableType: + active: false + Deprecation: + active: false + DontDowncastCollectionTypes: + active: false + DoubleMutabilityForCollection: + active: true + mutableTypes: + - 'kotlin.collections.MutableList' + - 'kotlin.collections.MutableMap' + - 'kotlin.collections.MutableSet' + - 'java.util.ArrayList' + - 'java.util.LinkedHashSet' + - 'java.util.HashSet' + - 'java.util.LinkedHashMap' + - 'java.util.HashMap' + ElseCaseInsteadOfExhaustiveWhen: + active: false + ignoredSubjectTypes: [ ] + EqualsAlwaysReturnsTrueOrFalse: + active: true + EqualsWithHashCodeExist: + active: true + ExitOutsideMain: + active: false + ExplicitGarbageCollectionCall: + active: true + HasPlatformType: + active: true + IgnoredReturnValue: + active: true + restrictToConfig: true + returnValueAnnotations: + - 'CheckResult' + - '*.CheckResult' + - 'CheckReturnValue' + - '*.CheckReturnValue' + ignoreReturnValueAnnotations: + - 'CanIgnoreReturnValue' + - '*.CanIgnoreReturnValue' + returnValueTypes: + - 'kotlin.sequences.Sequence' + - 'kotlinx.coroutines.flow.*Flow' + - 'java.util.stream.*Stream' + ignoreFunctionCall: [ ] + ImplicitDefaultLocale: + active: true + ImplicitUnitReturnType: + active: false + allowExplicitReturnType: true + InvalidRange: + active: true + IteratorHasNextCallsNextMethod: + active: true + IteratorNotThrowingNoSuchElementException: + active: true + LateinitUsage: + active: false + excludes: [ '**/test/**', '**/androidTest/**', '**/commonTest/**', '**/jvmTest/**', '**/androidUnitTest/**', '**/androidInstrumentedTest/**', '**/jsTest/**', '**/iosTest/**' ] + ignoreOnClassesPattern: '' + MapGetWithNotNullAssertionOperator: + active: true + MissingPackageDeclaration: + active: false + excludes: [ '**/*.kts' ] + NullCheckOnMutableProperty: + active: false + NullableToStringCall: + active: false + PropertyUsedBeforeDeclaration: + active: false + UnconditionalJumpStatementInLoop: + active: false + UnnecessaryNotNullCheck: + active: false + UnnecessaryNotNullOperator: + active: true + UnnecessarySafeCall: + active: true + UnreachableCatchBlock: + active: true + UnreachableCode: + active: true + UnsafeCallOnNullableType: + active: true + excludes: [ '**/test/**', '**/androidTest/**', '**/commonTest/**', '**/jvmTest/**', '**/androidUnitTest/**', '**/androidInstrumentedTest/**', '**/jsTest/**', '**/iosTest/**' ] + UnsafeCast: + active: true + UnusedUnaryOperator: + active: true + UselessPostfixExpression: + active: true + WrongEqualsTypeParameter: + active: true + +style: + active: true + AlsoCouldBeApply: + active: false + BracesOnIfStatements: + active: false + singleLine: 'never' + multiLine: 'always' + BracesOnWhenStatements: + active: false + singleLine: 'necessary' + multiLine: 'consistent' + CanBeNonNullable: + active: false + CascadingCallWrapping: + active: false + includeElvis: true + ClassOrdering: + active: false + CollapsibleIfStatements: + active: false + DataClassContainsFunctions: + active: false + conversionFunctionPrefix: + - 'to' + allowOperators: false + DataClassShouldBeImmutable: + active: false + DestructuringDeclarationWithTooManyEntries: + active: true + maxDestructuringEntries: 3 + DoubleNegativeLambda: + active: false + negativeFunctions: + - reason: 'Use `takeIf` instead.' + value: 'takeUnless' + - reason: 'Use `all` instead.' + value: 'none' + negativeFunctionNameParts: + - 'not' + - 'non' + EqualsNullCall: + active: true + EqualsOnSignatureLine: + active: false + ExplicitCollectionElementAccessMethod: + active: false + ExplicitItLambdaParameter: + active: true + ExpressionBodySyntax: + active: false + includeLineWrapping: false + ForbiddenAnnotation: + active: false + annotations: + - reason: 'it is a java annotation. Use `Suppress` instead.' + value: 'java.lang.SuppressWarnings' + - reason: 'it is a java annotation. Use `kotlin.Deprecated` instead.' + value: 'java.lang.Deprecated' + - reason: 'it is a java annotation. Use `kotlin.annotation.MustBeDocumented` instead.' + value: 'java.lang.annotation.Documented' + - reason: 'it is a java annotation. Use `kotlin.annotation.Target` instead.' + value: 'java.lang.annotation.Target' + - reason: 'it is a java annotation. Use `kotlin.annotation.Retention` instead.' + value: 'java.lang.annotation.Retention' + - reason: 'it is a java annotation. Use `kotlin.annotation.Repeatable` instead.' + value: 'java.lang.annotation.Repeatable' + - reason: 'Kotlin does not support @Inherited annotation, see https://youtrack.jetbrains.com/issue/KT-22265' + value: 'java.lang.annotation.Inherited' + ForbiddenComment: + active: true + comments: + - reason: 'Forbidden FIXME todo marker in comment, please fix the problem.' + value: 'FIXME:' + - reason: 'Forbidden STOPSHIP todo marker in comment, please address the problem before shipping the code.' + value: 'STOPSHIP:' + - reason: 'Forbidden TODO todo marker in comment, please do the changes.' + value: 'TODO:' + allowedPatterns: '' + ForbiddenImport: + active: false + imports: [ ] + forbiddenPatterns: '' + ForbiddenMethodCall: + active: false + methods: + - reason: 'print does not allow you to configure the output stream. Use a logger instead.' + value: 'kotlin.io.print' + - reason: 'println does not allow you to configure the output stream. Use a logger instead.' + value: 'kotlin.io.println' + ForbiddenSuppress: + active: false + rules: [ ] + ForbiddenVoid: + active: true + ignoreOverridden: false + ignoreUsageInGenerics: false + FunctionOnlyReturningConstant: + active: true + ignoreOverridableFunction: true + ignoreActualFunction: true + excludedFunctions: [ ] + LoopWithTooManyJumpStatements: + active: true + maxJumpCount: 1 + MagicNumber: + active: true + excludes: [ '**/test/**', '**/androidTest/**', '**/commonTest/**', '**/jvmTest/**', '**/androidUnitTest/**', '**/androidInstrumentedTest/**', '**/jsTest/**', '**/iosTest/**', '**/*.kts' ] + ignoreNumbers: + - '-1' + - '0' + - '1' + - '2' + ignoreHashCodeFunction: true + ignorePropertyDeclaration: true + ignoreLocalVariableDeclaration: false + ignoreConstantDeclaration: true + ignoreCompanionObjectPropertyDeclaration: true + ignoreAnnotation: false + ignoreNamedArgument: true + ignoreEnums: false + ignoreRanges: false + ignoreExtensionFunctions: true + MandatoryBracesLoops: + active: false + MaxChainedCallsOnSameLine: + active: false + maxChainedCalls: 5 + MaxLineLength: + active: true + maxLineLength: 120 + excludePackageStatements: true + excludeImportStatements: true + excludeCommentStatements: false + excludeRawStrings: true + MayBeConst: + active: true + ModifierOrder: + active: true + MultilineLambdaItParameter: + active: false + MultilineRawStringIndentation: + active: false + indentSize: 4 + trimmingMethods: + - 'trimIndent' + - 'trimMargin' + NestedClassesVisibility: + active: true + NewLineAtEndOfFile: + active: true + NoTabs: + active: false + NullableBooleanCheck: + active: false + ObjectLiteralToLambda: + active: true + OptionalAbstractKeyword: + active: true + OptionalUnit: + active: false + PreferToOverPairSyntax: + active: false + ProtectedMemberInFinalClass: + active: true + RedundantExplicitType: + active: false + RedundantHigherOrderMapUsage: + active: true + RedundantVisibilityModifierRule: + active: false + ReturnCount: + active: true + max: 2 + excludedFunctions: + - 'equals' + excludeLabeled: false + excludeReturnFromLambda: true + excludeGuardClauses: false + SafeCast: + active: true + SerialVersionUIDInSerializableClass: + active: true + SpacingBetweenPackageAndImports: + active: false + StringShouldBeRawString: + active: false + maxEscapedCharacterCount: 2 + ignoredCharacters: [ ] + ThrowsCount: + active: true + max: 2 + excludeGuardClauses: false + TrailingWhitespace: + active: false + TrimMultilineRawString: + active: false + trimmingMethods: + - 'trimIndent' + - 'trimMargin' + UnderscoresInNumericLiterals: + active: false + acceptableLength: 4 + allowNonStandardGrouping: false + UnnecessaryAbstractClass: + active: true + UnnecessaryAnnotationUseSiteTarget: + active: false + UnnecessaryApply: + active: true + UnnecessaryBackticks: + active: false + UnnecessaryBracesAroundTrailingLambda: + active: false + UnnecessaryFilter: + active: true + UnnecessaryInheritance: + active: true + UnnecessaryInnerClass: + active: false + UnnecessaryLet: + active: false + UnnecessaryParentheses: + active: false + allowForUnclearPrecedence: false + UntilInsteadOfRangeTo: + active: false + UnusedImports: + active: false + UnusedParameter: + active: true + allowedNames: 'ignored|expected' + UnusedPrivateClass: + active: true + UnusedPrivateMember: + active: true + allowedNames: '' + ignoreAnnotated: [ 'Preview ' ] + UnusedPrivateProperty: + active: true + allowedNames: '_|ignored|expected|serialVersionUID' + UseAnyOrNoneInsteadOfFind: + active: true + UseArrayLiteralsInAnnotations: + active: true + UseCheckNotNull: + active: true + UseCheckOrError: + active: true + UseDataClass: + active: false + allowVars: false + UseEmptyCounterpart: + active: false + UseIfEmptyOrIfBlank: + active: false + UseIfInsteadOfWhen: + active: false + ignoreWhenContainingVariableDeclaration: false + UseIsNullOrEmpty: + active: true + UseLet: + active: false + UseOrEmpty: + active: true + UseRequire: + active: true + UseRequireNotNull: + active: true + UseSumOfInsteadOfFlatMapSize: + active: false + UselessCallOnNotNull: + active: true + UtilityClassWithPublicConstructor: + active: true + VarCouldBeVal: + active: true + ignoreLateinitVar: false + WildcardImport: + active: true + excludeImports: + - 'java.util.*' diff --git a/gradle/libs.versions.toml b/gradle/libs.versions.toml index a289f4028..c0e7bddd9 100644 --- a/gradle/libs.versions.toml +++ b/gradle/libs.versions.toml @@ -80,7 +80,7 @@ mockk = "io.mockk:mockk:1.12.2" mockk-android = "io.mockk:mockk-android:1.12.2" turbine = "app.cash.turbine:turbine:0.12.3" junit = "junit:junit:4.13.2" -detekt-gradle = "io.gitlab.arturbosch.detekt:detekt-gradle-plugin:1.18.1" +detekt-gradle = "io.gitlab.arturbosch.detekt:detekt-gradle-plugin:1.23.6" ktlint-gradle = "org.jlleitschuh.gradle:ktlint-gradle:10.2.0" mlkit-barcodescanning = "com.google.android.gms:play-services-mlkit-barcode-scanning:18.3.0" mlkit-textrecognition = "com.google.android.gms:play-services-mlkit-text-recognition:19.0.0"