Android app suddenly not compatible with devices - android

I have an Android app that has been in the Google Play store for about two years now (https://play.google.com/store/apps/details?id=dkh.idex) with API level 7+ and support for all screen sizes. It uses a few permissions (ACCESS_NETWORK_STATE, INTERNET, READ_EXTERNAL_STORAGE, WRITE_EXTERNAL_STORAGE).
On April 22 2013 I uploaded a version (version code 44) that worked fine on all my users devices. A month later, on May 22 2013 I uploaded a new version with some minor changes (version code 45), but the last few days (starting May 27) a lot of users has complained to me that their devices no longer are compatible with the newest version of my app. These users have been using the app with no such problems for up to two years. Some devices are still able to upgrade to the newest version, but others get the message that their device is not compatible when trying to upgrade (mind you, they already have an older version of the app). I was able to install the application directly through ADB (USB) on a device that said it was not compatible in the Google Play store (a Samsung Galaxy Tab 10.1, old version).
I looked through my changesets of my files, and the only change I have made in the AndroidManifest.xml between the two releases are updating the version code and version number. I have not changed any use permissions, supported screen sizes, supported API levels or even added any activities or changed debug settings.
Here is my AndroidManifest.xml:
<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="dkh.idex"
android:versionName="3.2.11" android:versionCode="45">
<supports-screens
android:smallScreens="true"
android:normalScreens="true"
android:largeScreens="true"
android:anyDensity="true" />
<uses-sdk android:minSdkVersion="7"/>
<uses-permission android:name="android.permission.INTERNET"></uses-permission>
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE"></uses-permission>
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE"/>
<application android:name="dkh.classes.MyApp" android:label="#string/app_name" android:debuggable="false" android:icon="#drawable/ic_launcher_idex_v3">
<activity android:name=".idex"
android:label="#string/app_name"
android:screenOrientation="portrait">
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</activity>
<activity android:name=".Form2"
android:label="#string/app_name"
android:screenOrientation="portrait"
android:configChanges="orientation">
</activity>
<activity android:name=".InfoForm"
android:label="#string/app_name"
android:screenOrientation="portrait">
</activity>
<activity android:name=".INSTAForm"
android:label="#string/app_name"
android:launchMode="standard"
android:screenOrientation="portrait">
</activity>
<activity android:name=".HygieneForm"
android:label="#string/app_name"
android:screenOrientation="portrait">
</activity>
<activity android:name=".CommentForm"
android:label="#string/app_name"
android:screenOrientation="portrait">
</activity>
<activity android:name=".AddReqChooseForm"
android:label="#string/app_name"
android:screenOrientation="portrait">
</activity>
<activity android:name=".AddReqForm"
android:label="#string/app_name"
android:screenOrientation="portrait">
</activity>
<activity android:name=".FTPForm" android:label="#string/app_name" android:screenOrientation="portrait"></activity>
<activity android:name=".SyncForm" android:label="#string/app_name" android:screenOrientation="portrait"></activity>
<activity android:name=".DrawTestForm" android:label="#string/app_name" android:configChanges="keyboardHidden|orientation"></activity>
<activity android:name="StatisticsForm" android:screenOrientation="portrait" android:label="#string/app_name"></activity>
<activity android:name="PhotoGallery" android:screenOrientation="portrait" android:label="#string/app_name"></activity>
<activity android:name="PhotoView" android:label="#string/app_name"></activity>
<activity android:name="ParametersForm" android:label="#string/app_name" android:screenOrientation="portrait" android:windowSoftInputMode="adjustPan"></activity>
<activity android:name="PropertiesForm" android:label="#string/app_name" android:screenOrientation="portrait" android:windowSoftInputMode="adjustPan"></activity>
<activity android:screenOrientation="portrait" android:name="InspectionChangeForm" android:label="#string/app_name"></activity>
<activity android:name="AdvancedSyncWindow" android:label="#string/app_name" android:screenOrientation="portrait"></activity>
<service android:process=":image_process" android:name=".ImageUploadService"></service>
<activity android:name=".HelpWindow" android:label="#string/app_name"></activity>
<activity android:name="RecoverView"></activity>
<activity android:name="InspectionCommentForm" ></activity>
</application>
</manifest> `
In the rest of my code I have added some texts to my resource files and made some standard minor changes, but nothing that weren't in the app already in some form.
I am really puzzled by this problem. Does anyone know what could be the cause of this or know if Google has changed anything that could have an effect on this? Please ask if you need more information.

I solved it.
The problem was that Google Play will filter applications based on the device screen size, and because xlargeScreens are not supported in API 7 (version 2.1) the filter will be set to false on these devices. This has not been enforced until end of May. My app had worked on the exact same specification for two years, but I suspect that Google Play has made an update to enforce this constraint.
The solution: If you have an app that is developed for API 7 but you want it to be available on xlargeScreens devices, you have to set in your manifest
<uses-sdk
android:minSdkVersion="7"
android:targetSdkVersion="9" />
If either minSdkVersion or targetSdkVersion is 9 or larger, Google Play will allow xlargeScreen devices to see your app.

Related

Camera2 API compatibility issues with google play store

I have developed an android app that uses the camera2 API. I am able to run this app on my own physical device when I'm debugging, but when I try to publish the app to the google play store, it says that my device isn't compatible - in fact, no devices are compatible with my app.
I have been in contact with google support, and they said that "your app is not compatible with most devices due to a conflict in your app’s manifest because of the following missing device feature: android.hardware.camera2. "
I have noticed that the min-sdk version in my gradle file was set to 15.
So my question is: Will my app become compatible with my devices if I change the min-sdk version to 21, or do I need to rewrite my entire code to use the deprecated camera API instead?
Thanks in advance.
*Edit:
This is my android manifest:
<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="...">
<uses-feature
android:name="android.hardware.camera2"
android:required="true"/>
<uses-permission android:name="android.permission.CAMERA" />
<uses-permission android:name="android.permission.INTERNET" />
<application
android:allowBackup="true"
android:icon="#mipmap/ic_launcher"
android:name=".app.AppController"
android:label="#string/app_name"
android:supportsRtl="true"
android:theme="#style/AppTheme">
<meta-data
android:name="com.google.android.gms.vision.DEPENDENCIES"
android:value="barcode"/>
<activity
android:name=".MainActivity"
android:label="#string/app_name"
android:theme="#style/AppTheme.NoActionBar"
android:screenOrientation="portrait">
</activity>
<activity
android:name=".ResultsActivity"
android:label="#string/app_name"
android:theme="#style/AppTheme.NoActionBar"
android:screenOrientation="portrait">
</activity>
<activity
android:name=".QRScanner"
android:label="#string/app_name"
android:theme="#style/AppTheme.NoActionBar"
android:screenOrientation="portrait">
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</activity>
</application>
There is no such feature as "android.hardware.camera2", so if you require it for your app to be installable on a device, you won't be installable anywhere, since no device anywhere reports that feature.
The camera2 API exists on all devices running Android 5.0 or later, it doesn't have a feature. Remove the feature line, and use the min-sdk line if you don't want to deal with devices too old to support camera2.

android configChange:orientation and manifest does not work

I have used a Web view. which loads webpage. When i orientation is changed it reloads. I want to stop reloading. I did following change in manifest XML File.
It works in android 2.2 but not in android 4.0. I am a beginner can any one provide solution.
My Manifest.xml is;
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="application.eag"
android:versionCode="1"
android:versionName="1.0" >
<uses-sdk
android:minSdkVersion="8"
android:targetSdkVersion="17" />
<uses-permission android:name="android.permission.INTERNET" />
<application
android:icon="#drawable/ic_launcher"
android:label="#string/app_name"
android:theme="#style/AppTheme" >
<activity
android:name=".MainActivity"
android:label="#string/title_activity_main"
android:configChanges="orientation|screenSize|keyboardHidden">
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</activity>
</application>
</manifest>
<activity
android:name=".ActivityName"
android:configChanges="orientation|screenSize|keyboardHidden"/>
Use screenSize for newly version. orientation might not be supported in some version, need to use screenSize for configChanges
This one worked for me:
<activity android:name=".YourActivity"
android:configChanges="orientation|screenSize|keyboardHidden">
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</activity>
I am using like the following and it works for me.
<activity
android:name="com.myapp.MainActivity"
android:configChanges="orientation|keyboardHidden"/>
Made changes as answered by Avadhani Y
1) Added following in manifest
<activity
android:name=".ActivityName"
android:configChanges="orientation|screenSize|keyboardHidden"/>
2) changed manifest as
<uses-sdk android:minSdkVersion="8" android:targetSdkVersion="17"/>
3) in project.properties set the following value
# Project target.
target=android-13
Use your activity like this ...
<activity
android:name=".UserLoginActivity"
android:configChanges="keyboardHidden|orientation|screenSize"
android:screenOrientation="unspecified" >
</activity>
I couldn't get any of these to work, but then I got it (not sure what was going on but thought I'd elaborate on other answers to save people time). I found the below to work for my app (1 line in your manifest INSIDE the tag, for the activity you want this behavior for. I also discovered it completely depends on your app on what you need here. For a complete list see http://developer.android.com/guide/topics/manifest/activity-element.html#config
And by 'doesn't work', I mean the onDestroy() method got called every time I rotated my device. See Why not use always android:configChanges="keyboardHidden|orientation"? for reasons you likely shouldn't use this.
Manifest.xml:
<activity
android:name="com.example.MainActivity"
android:label="#string/app_name"
android:launchMode="singleTop"
android:configChanges="orientation|screenSize"
>

Android app is shown as not compatible in play store

I have published a new update of my App. After publishing it got a warning like "Warning: Your active APK supports less devices then the previous APK. Some users won't get the update."
So i've compared the details of the current and the prior APK. There is only one difference: The new one has the additional entry "Native Platform: simple-xml.2.6.9.jar".
Do you think that there is a problem with it? Acutally i've intergrated the .jar into my android project.
Additionally, the developer console shows me that the app is now compatible with 0 devices... if i search for a certain device i get a notice that it's because of my manifest settings.
<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="edu.kit.aifb.nukit"
android:versionCode="8"
android:versionName="#string/app_versionName" >
<uses-permission android:name="android.permission.INTERNET" />
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" />
<uses-permission android:name="android.permission.VIBRATE"/>
<uses-sdk
android:minSdkVersion="7"
android:targetSdkVersion="17" />
<application
android:icon="#drawable/ic_launcher"
android:label="#string/app_name"
android:theme="#style/Theme.KIT.Styled"
android:allowBackup="true" >
<activity
android:name="edu.kit.aifb.nukit.gui.SplashScreenActivity"
android:label="#string/app_name"
android:screenOrientation="portrait"
android:theme="#style/Theme.Sherlock.Light.NoActionBar"
android:clearTaskOnLaunch="true" >
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</activity>
<activity
android:name="edu.kit.aifb.nukit.gui.ChooseCourseActivity"
android:screenOrientation="portrait"></activity>
<activity
android:name="edu.kit.aifb.nukit.gui.QuestioningAndVotingActivity"
android:screenOrientation="portrait"
android:windowSoftInputMode="stateHidden"></activity>
<activity
android:name="edu.kit.aifb.nukit.gui.AnswerQuestionActivity"
android:screenOrientation="portrait"></activity>
<activity
android:name="edu.kit.aifb.nukit.gui.ShowResultsActivity"
android:screenOrientation="portrait"></activity>
<activity
android:name="edu.kit.aifb.nukit.gui.ImpressumActivity"
android:screenOrientation="portrait"></activity>
<activity
android:name="edu.kit.aifb.nukit.gui.LicensesActivity"
android:screenOrientation="portrait"
android:hardwareAccelerated="false"></activity>
<activity
android:name="edu.kit.aifb.nukit.gui.survey.SurveyListActivity"
android:screenOrientation="portrait"></activity>
<activity
android:name="edu.kit.aifb.nukit.gui.survey.QuestionActivity"
android:screenOrientation="portrait"
android:parentActivityName=".SurveyListActivity" >
<meta-data
android:name="android.support.PARENT_ACTIVITY"
android:value=".SurveyListActivity" />
</activity>
<activity
android:name="edu.kit.aifb.nukit.gui.survey.SurveyResultsActivity"
android:label="SurveyResultsActivity"
android:parentActivityName=".SurveyListActivity">
<meta-data
android:name="android.support.PARENT_ACTIVITY"
android:value=".SurveyListActivity" />
</activity>
</application>
if i install the apk directly on my device, it works fine.
This should probably be due to changes done in your Android Manifest relating to max and min sdk versions
<uses-sdk android:minSdkVersion="integer"
android:targetSdkVersion="integer"
android:maxSdkVersion="integer" />
If this SDK version range has been altered, your new updated app might support lesser number of devices.
Alright, i fixed it.
The problem was that actualy only the SurveyLib.jar is using simple-xml-2.6.9.jar and the simplexml.jar was included within the SurveyLib.jar. So i think there was a problem dexing the simplexml.jar within surveylib.jar.
i've created the surveylib.jar again without simplexml.jar but included the simplexml.jar to the libs folder of my app.
now it works fine. thanks to you all for your help.

android - "your device isn't compatible with this version"

I put an app in the play store and my friend, who is running 4.1(Nexus 7), got the following message when trying to install my app : "your device isn't compatible with this version". Why this came? Please can any one help me.
Manifeast file
< ?xml version="1.0" encoding="utf-8"?>
< manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="com.ibkr.pcg"
android:versionCode="3"
android:versionName="1.1">
< uses-sdk android:minSdkVersion="7"
android:targetSdkVersion="8"/>
<uses-permission android:name="android.permission.INTERNET"></uses-permission>
<uses-permission android:name="android.permission.CAMERA" />
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" ></uses-permission>
<!-- C2DM Permissions Start -->
<!-- Only this application can receive the messages and registration result -->
<permission android:name="com.ibkr.pcg.permission.C2D_MESSAGE" android:protectionLevel="signature" />
<uses-permission android:name="com.ibkr.pcg.permission.C2D_MESSAGE" />
<!-- This app has permission to register and receive message -->
<uses-permission android:name="com.google.android.c2dm.permission.RECEIVE" />
<!-- End of the C2DM Permissions -->
<application android:icon="#drawable/pcgicon"
android:label="#string/app_name"
android:theme="#android:style/Theme.NoTitleBar.Fullscreen"
android:name="MyApplication"
android:debuggable="true">
<activity android:name=".PriceCheckGuruSplash"
android:label="#string/app_name">
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</activity>
<!-- Only C2DM servers can send messages for the app. If permission is not set - any other app can generate it -->
<receiver
android:name=".C2DMMessageReciever" android:permission="com.google.android.c2dm.permission.SEND" >
<!-- Receive the actual message -->
<intent-filter >
<action android:name="com.google.android.c2dm.intent.RECEIVE" >
</action>
<category android:name="com.ibkr.pcg" />
</intent-filter>
</receiver>
<receiver
android:name=".C2DMRegistrationReceiver"
android:permission="com.google.android.c2dm.permission.SEND" >
<intent-filter >
<action android:name="com.google.android.c2dm.intent.REGISTRATION" >
</action>
<category android:name="com.ibkr.pcg" />
</intent-filter>
</receiver>
<activity android:name="MessageReceivedActivty" android:screenOrientation="portrait"/>
<activity android:name="LoginScreen" android:screenOrientation="portrait"> </activity>
<activity android:name="RegistrationScreen" android:screenOrientation="portrait"> </activity>
<activity android:name="ForgotPasswordScreen" android:screenOrientation="portrait"> </activity>
<activity android:name="UserPreferences" android:screenOrientation="portrait"> </activity>
<activity android:name="TrackedItems" android:screenOrientation="portrait"> </activity>
<activity android:name="WebPage" android:screenOrientation="portrait"> </activity>
<activity android:name="CustomTabActivity" android:screenOrientation="portrait"> </activity>
<activity android:name="TabGroup1Activity" android:screenOrientation="portrait"> </activity>
<activity android:name="TabGroup2Activity" android:screenOrientation="portrait"> </activity>
<activity android:name="TabGroup3Activity" android:screenOrientation="portrait"> </activity>
<activity android:name="TabGroup4Activity" android:screenOrientation="portrait"> </activity>
<activity android:name="SearchScreen" android:screenOrientation="portrait"> </activity>
<activity android:name="SearchResultsScreen" android:screenOrientation="portrait"></activity>
<activity android:name="ProductDisplay" android:screenOrientation="portrait"></activity>
<activity android:name="VendorsDisplay" android:screenOrientation="portrait"></activity>
<activity android:name="Filter" android:screenOrientation="portrait"></activity>
<activity android:name="barcodeScanner" android:screenOrientation="portrait"></activity>
<activity android:name="ScannerPage" android:screenOrientation="portrait"></activity>
<activity android:name="Linegraphpage" android:screenOrientation="landscape"></activity>
<activity android:name="org.achartengine.GraphicalActivity" android:screenOrientation="landscape"/>
<activity android:name="org.acra.CrashReportDialog"
android:theme="#android:style/Theme.Dialog"
android:launchMode="singleInstance"
android:excludeFromRecents="true"
android:finishOnTaskLaunch="true" />
</application>
< /manifest>
//remove this android:targetSdkVersion="8"
and Nexus 7 doesn't have back camera features.
<uses-permission android:name="android.permission.CAMERA" />
Note: If you are using the camera via an intent, your application does not need to request this permission.
Camera Features - Your application must also declare use of camera features, for example:
<uses-feature android:name="android.hardware.camera" />
For a list of camera features, see the manifest Features Reference.
Adding camera features to your manifest causes Google Play to prevent your application from being installed to devices that do not include a camera or do not support the camera features you specify. For more information
If your application can use a camera or camera feature for proper operation, but does not require it, you should specify this in the manifest by including the android:required attribute, and setting it to false:
Note: you need to mention supports-screens
It's because of your 'android.permission.ACCESS_NETWORK_STATE' permission- the device doesn't have a cell phone modem, you need to put android:required="false" in the permission to allow it to be installed on devices that don't support it
To control filtering, always explicitly declare hardware features in
elements, rather than relying on Google Play to
"discover" the requirements in elements. Then, if
you want to disable filtering for a particular feature, you can add a
android:required="false" attribute to the declaration.
http://developer.android.com/guide/topics/manifest/uses-permission-element.html
Like others already suggested - the camera could be an issue here. There's a good post on the android developers blog about nexus 7. Basically it only has a single front facing camera, so your app asking for the default camera requirement will fail....
basically you need to extend the request to say it's not critical, and then handle the details in your app...
<uses-feature android:name="android.hardware.camera"
android:required="false"/>
For lots more info, follow the link
http://android-developers.blogspot.com.au/2012/07/getting-your-app-ready-for-jelly-bean.html
android:targetSdkVersion should be the highest SDK available when you are building the app, unless you have very specific reasons not to. Maybe you want to guarantee newer methods and APIs will not be called because you must work right on a specific device, even if it means sacrificing behavior on newer ones.
Most of the time, download the latest SDK and set android:targetSdkVersion to the latest version.
Just use this
<uses-sdk android:minSdkVersion="7" />
Use the following :
<supports-screens
android:largeScreens="true"
android:normalScreens="true"
android:smallScreens="true"
android:xlargeScreens="true" />
<uses-sdk
android:minSdkVersion="7"
android:targetSdkVersion="16" /> //or just remove the targetSdkVersion, altough it is not recommended
Always attributes defined in Manifest Filters out Your app By Google Playstore to some devices.
For example:
Declared specific Target Sdk Version.
Defined Camera permission(Will filter devices without Camera)
Uses Feature Camera.
SIM enabled device.
Device with Wifi.
So, Before releasing your app you have to keep in mind that you have to reach maximum devices for your target than you have to Opt out some of the features and Permissions and most of the time Sdk version target.
Hope this gives you idea about releasing App.

Android application no more compatible on Market

I've developed an App using level API 10 (2.3.3 SDK version), I've published it on Android Market and all has gone fine. My Application has FINE and COARSE location, INTERNET and NETWORK STATE as uses permission.
Next, I've tried to extend compatibility to level API 8 (2.2). After I've published the new apk on market the App results no more compatible with my device (I've a Samsung GT-I9100, with 2.3.6 Android version).
I've tried to delete cache but nothing, my device is no more compatible.
But if I install the apk via file system the App perfectly works.
EDIT:
Here my Android Manifest
<manifest package="com.agora.md" android:versionCode="16" android:versionName="1.1.15" xmlns:android="http://schemas.android.com/apk/res/android">
<uses-permission android:name="android.permission.INTERNET"/>
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE"/>
<uses-permission android:name="android.permission.ACCESS_FINE_LOCATION"/>
<uses-permission android:name="android.permission.ACCESS_COARSE_LOCATION"/>
<uses-sdk android:minSdkVersion="8"/>
<supports-screens android:smallScreens="false" android:largeScreens="true" android:normalScreens="true"/>
<application
android:icon="#drawable/icon_md1"
android:label="#string/app_name" android:name="MDApplication" >
<activity
android:label="#string/app_name"
android:name=".service.activity.MDSplashActivity"
android:screenOrientation="portrait">
<intent-filter >
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</activity>
<activity android:screenOrientation="portrait" android:label="#string/app_name"
android:name=".service.activity.MDMainActivity" android:launchMode="singleTask">
</activity>
<activity android:name=".service.activity.MDNewsActivity" android:launchMode="singleTask"
android:screenOrientation="portrait"></activity>
<activity android:name=".service.activity.MDMagnificiActivity" android:launchMode="singleTask"
android:screenOrientation="portrait"></activity>
<activity android:name=".service.activity.MDNewsDetailsActivity"
android:screenOrientation="portrait"></activity>
<uses-library android:name="com.google.android.maps"/>
<activity android:name=".service.activity.MDMapActivity" android:launchMode="singleTask"
android:screenOrientation="portrait"></activity>
<activity android:name=".service.activity.MDInfoActivity"
android:screenOrientation="portrait"></activity>
<activity android:name=".service.activity.MDVolantinoActivity"
android:screenOrientation="portrait"></activity>
<activity android:name=".service.activity.MDMapDetailsActivity"
android:screenOrientation="portrait"></activity>
</application>
</manifest>
Someone can help me?
Thanks
UPDATE
After a month I've checked on Market and now, incredibly, my app is visible on the store. I don't now it's ok because I've made no changes from that.
I think it was a mistake of the store or, probably, a bad value in cache that now has been erased.
However, thanks to all for your support
The supports-screens tag is used ONLY by the Android market to filter out devices based on the size of screen the device has. If you don't define a supports-screens tag, then the market doesn't filter them.
However, if you DO define supports-screens any device sizes not listed will default to false.
The Samsung Galaxy SII (your device) I believe is an xlarge screen size. Change your supports-screens tag to the following:
<supports-screens android:xlargeScreens="true" android:smallScreens="false" android:largeScreens="true" android:normalScreens="true" />
(note: I added android:xlargeScreens="true")
After that you should see your app in the market again.
Similar issue here. I don't have the supports-screens tag in my AndroidManifest.xml, but I'm getting incompatibility complaints from users with the Samsung Galaxy S 2 (GT-I9100), Android version 2.3.6. It works with other versions of Android.
Anyone else seen this?

Categories

Resources