Disable "Answers" but not "Crashlytics" - crashlytics

When installing "Crashlytics" in my Android App, it automatically installs "Answers". I only want to install "Crashlytics" and want to have "Answers" disabled. Does anyone know how to do that?
build.gradle
dependencies {
compile('com.crashlytics.sdk.android:crashlytics:2.5.5#aar') {
transitive = true;
}
Thanks!

Mike from Fabric and Crashlytics here.
As you saw, Crashlytics by default includes Answers. If you don't want Answers enabled on your app, then you want to invoke CrashlyticsCore() when building your app instead of Crashlytics.
For example, have these as your imports:
import com.crashlytics.android.Crashlytics;
import com.crashlytics.android.core.CrashlyticsCore;
import io.fabric.sdk.android.Fabric;
Then when you initialize Fabric, use:
Fabric.with(this, new CrashlyticsCore());
and that will initialize only the crash reporting side of things.

I think it is not possible at the moment, because Crashlytics is making an Answers instance:
public Crashlytics build() {
if(this.coreBuilder != null) {
if(this.core != null) {
throw new IllegalStateException("Must not use Deprecated methods delay(), disabled(), listener(), pinningInfoProvider() with core()");
}
this.core = this.coreBuilder.build();
}
if(this.answers == null) {
this.answers = new Answers();
}
if(this.beta == null) {
this.beta = new Beta();
}
if(this.core == null) {
this.core = new CrashlyticsCore();
}
return new Crashlytics(this.answers, this.beta, this.core);
}
Crashlytics(Answers answers, Beta beta, CrashlyticsCore core) is not public, so we cannot instanciate this. Also the answers field is final, so you cannot override it. I think there is now way to let the user decide if they want to use answers.
Hey Fabric/Google, you should make a programmatically way to opt out for a session, to give the programmer the option to let the user decide if they want to be counted in some way.
EDIT
My solution is to to use a wraper for all needed funtioncs and init, feel free to use it:
public class AnalyticsWrapper {
static AnalyticsWrapper instance;
public static void initialize(Context context, boolean optOut) {
if (instance != null) throw new IllegalStateException("AnalyticsWrapper must only be initialized once");
instance = new AnalyticsWrapper(context.getApplicationContext(), optOut);
}
public static AnalyticsWrapper getInstance() {
if (instance == null) throw new IllegalStateException("AnalyticsWrapper must be initialized before");
return instance;
}
final boolean optOut;
private AnalyticsWrapper(Context context, boolean optOut) {
this.optOut = optOut;
initFabric(context);
}
public boolean isOptOut() {
return optOut;
}
private void initFabric(Context context) {
if (!optOut) {
if (!BuildConfig.DEBUG) {
Timber.plant(new CrashlyticsLogExceptionTree());
Timber.plant(new CrashlyticsLogTree(Log.INFO));
}
Crashlytics crashlyticsKit = new Crashlytics.Builder().core(
new CrashlyticsCore.Builder().disabled(BuildConfig.DEBUG)
.build())
.build();
Fabric fabric = new Fabric.Builder(context).kits(crashlyticsKit)
.debuggable(BuildConfig.DEBUG)
.build();
Fabric.with(fabric);
}
}
public void crashlyticsSetString(String key, String value) {
if (!optOut) {
Crashlytics.setString(key, value);
}
}
public void logException(Throwable throwable) {
if (!optOut) {
Crashlytics.logException(throwable);
}
}
public void logEvent(CustomEvent event) {
if (!optOut) {
Answers.getInstance()
.logCustom(event);
}
}
}

Related

recyclerview filter in is not working in android studio

I have coded getFilter() in adapter class and onQueryTextChange in mainactivity but don't know whats the prob it is not filtering nor searching please help I need to implement a search filter RecyclerView the list must be filtered while typing.
This part is in my Mainactivity
#Override
public boolean onCreateOptionsMenu(Menu menu) {
getMenuInflater().inflate(R.menu.search, menu);
MenuItem item = menu.findItem(R.id.action_search);
SearchView searchView = (SearchView) item.getActionView();
searchView.setImeOptions(EditorInfo.IME_ACTION_DONE);
searchView.setOnQueryTextListener(new SearchView.OnQueryTextListener() {
#Override
public boolean onQueryTextSubmit(String query) {
return false;
}
#Override
public boolean onQueryTextChange(String newText) {
BalanceReportAdapter myClass = new BalanceReportAdapter(jsonResponses,
BalanceReport.this);
myClass.getFilter().filter(newText);
return false;
}
});
return super.onCreateOptionsMenu(menu);
}
This part is in my Adapter.class
Filter filter = new Filter() {
#Override
protected FilterResults performFiltering(CharSequence constaint) {
List<BalanceReportModel> filteredList = new ArrayList<>();
if (constaint.toString().isEmpty()) {
filteredList.addAll(retrievedResponses);
Log.e("you are here1",filteredList.toString());
} else {
for (BalanceReportModel patient : retrievedResponsesAll) {
if
(patient.getcustomer().toLowerCase().contains(constaint.toString().toLowerCase()))
{
filteredList.add(patient);
}
}
Log.e("you are here2",retrievedResponses.toString());
}
FilterResults filterResults = new FilterResults();
filterResults.values = filteredList;
return filterResults;
}
#SuppressLint("NotifyDataSetChanged")
#Override
protected void publishResults(CharSequence constraint, FilterResults filterResults) {
Log.e("you are here3",filterResults.toString());
retrievedResponses.clear();
retrievedResponses.addAll((Collection<? extends BalanceReportModel>) filterResults.values);
notifyDataSetChanged();
}
};
I have tried several times but not yet succeeded Please someone help me. Is there any other way to make it work?
Correct me if i am wrong
It seems you are creating a new adapter each time in your onQueryTextChange
This instance of adapter is not assigned to recyclerView anywhere after that. I would recommend having one instance of adapter somewhere at the top-level and just call for that instance, and .filter logic

Upgrade Solution to use FluentValidation Ver 10 Exception Issue

Please I need your help to solve FluentValidation issue. I have an old desktop application which I wrote a few years ago. I used FluentValidation Ver 4 and Now I'm trying to upgrade this application to use .Net framework 4.8 and FluentValidation Ver 10, but unfortunately, I couldn't continue because of an exception that I still cannot fix.
I have this customer class:
class Customer : MyClassBase
{
string _CustomerName = string.Empty;
public string CustomerName
{
get { return _CustomerName; }
set
{
if (_CustomerName == value)
return;
_CustomerName = value;
}
}
class CustomerValidator : AbstractValidator<Customer>
{
public CustomerValidator()
{
RuleFor(obj => obj.CustomerName).NotEmpty().WithMessage("{PropertyName} is Empty");
}
}
protected override IValidator GetValidator()
{
return new CustomerValidator();
}
}
This is my base class:
class MyClassBase
{
public MyClassBase()
{
_Validator = GetValidator();
Validate();
}
protected IValidator _Validator = null;
protected IEnumerable<ValidationFailure> _ValidationErrors = null;
protected virtual IValidator GetValidator()
{
return null;
}
public IEnumerable<ValidationFailure> ValidationErrors
{
get { return _ValidationErrors; }
set { }
}
public void Validate()
{
if (_Validator != null)
{
var context = new ValidationContext<Object>(_Validator);
var results = _Validator.Validate(context); **// <======= Exception is here in this line**
_ValidationErrors = results.Errors;
}
}
public virtual bool IsValid
{
get
{
if (_ValidationErrors != null && _ValidationErrors.Count() > 0)
return false;
else
return true;
}
}
}
When I run the application test I get the below exception:
System.InvalidOperationException HResult=0x80131509 Message=Cannot
validate instances of type 'CustomerValidator'. This validator can
only validate instances of type 'Customer'. Source=FluentValidation
StackTrace: at
FluentValidation.ValidationContext1.GetFromNonGenericContext(IValidationContext context) in C:\Projects\FluentValidation\src\FluentValidation\IValidationContext.cs:line 211 at FluentValidation.AbstractValidator1.FluentValidation.IValidator.Validate(IValidationContext
context)
Please, what is the issue here and How can I fix it?
Thank you
Your overall implementation isn't what I'd consider normal usage however the problem is that you're asking FV to validate the validator instance, rather than the customer instance:
var context = new ValidationContext<Object>(_Validator);
var results = _Validator.Validate(context);
It should start working if you change it to:
var context = new ValidationContext<object>(this);
var results = _Validator.Validate(context);
You're stuck with using the object argument for the validation context unless you introduce a generic argument to the base class, or create it using reflection.

Override the dependencies added during running a project as an Eclipse Application

I am trying to write a custom launch configuration while running a plugin project as an eclipse application. I have to run the plugin with limited dependencies. Is it possible to override methods in org.eclipse.pde.launching.EclipseApplicationLaunchConfiguration ? If yes then how do I do it ?
You can't easily override the methods in EclipseApplicationLaunchConfiguration. That would require writing a new launch configuration - probably by using the org.eclipse.debug.core.launchConfigurationTypes extension point to define a new launch type.
EclipseApplicationLaunchConfiguration always uses the settings from the current entry in the 'Eclipse Application' section of the 'Run Configurations'. You can always edit the run configuration to change the dependencies or create another run configuration with different dependencies.
To write a custom configuration file
Extend the class org.eclipse.jdt.junit.launcher.JUnitLaunchShortcut
Override the method createLaunchConfiguration
Invoking super.createLaunchConfiguration(element) will return a ILaunchConfigurationWorkingCopy
Use the copy and set your own attributes that have to be modified
Attributes can be found in IPDELauncherConstants
Eclipse by default runs all the projects found in the workspace. This behavior can be modified by using the configuration created and overriding it with custom configuration.
public class LaunchShortcut extends JUnitLaunchShortcut {
class PluginModelNameBuffer {
private List<String> nameList;
PluginModelNameBuffer() {
super();
this.nameList = new ArrayList<>();
}
void add(final IPluginModelBase model) {
this.nameList.add(getPluginName(model));
}
private String getPluginName(final IPluginModelBase model) {
IPluginBase base = model.getPluginBase();
String id = base.getId();
StringBuilder buffer = new StringBuilder(id);
ModelEntry entry = PluginRegistry.findEntry(id);
if ((entry != null) && (entry.getActiveModels().length > 1)) {
buffer.append('*');
buffer.append(model.getPluginBase().getVersion());
}
return buffer.toString();
}
#Override
public String toString() {
Collections.sort(this.nameList);
StringBuilder result = new StringBuilder();
for (String name : this.nameList) {
if (result.length() > 0) {
result.append(',');
}
result.append(name);
}
if (result.length() == 0) {
return null;
}
return result.toString();
}
}
#Override
protected ILaunchConfigurationWorkingCopy createLaunchConfiguration(final IJavaElement element)
throws CoreException {
ILaunchConfigurationWorkingCopy configuration = super.createLaunchConfiguration(element);
configuration.setAttribute(IJavaLaunchConfigurationConstants.ATTR_VM_ARGUMENTS, "memory");
configuration.setAttribute(IPDELauncherConstants.USE_PRODUCT, false);
configuration.setAttribute(IPDELauncherConstants.USE_DEFAULT, false);
configuration.setAttribute(IPDELauncherConstants.AUTOMATIC_ADD, false);
addDependencies(configuration);
return configuration;
}
#SuppressWarnings("restriction")
private void addDependencies(final ILaunchConfigurationWorkingCopy configuration) throws CoreException {
PluginModelNameBuffer wBuffer = new PluginModelNameBuffer();
PluginModelNameBuffer tBuffer = new PluginModelNameBuffer();
Set<IPluginModelBase> addedModels = new HashSet<>();
String projectName = configuration.getAttribute(IJavaLaunchConfigurationConstants.ATTR_PROJECT_NAME, "");
IProject project = ResourcesPlugin.getWorkspace().getRoot().getProject(projectName);
IPluginModelBase model = PluginRegistry.findModel(project);
wBuffer.add(model);
addedModels.add(model);
IPluginModelBase[] externalModels = PluginRegistry.getExternalModels();
for (IPluginModelBase externalModel : externalModels) {
String id = externalModel.getPluginBase().getId();
if (id != null) {
switch (id) {
case "org.eclipse.ui.ide.application":
case "org.eclipse.equinox.ds":
case "org.eclipse.equinox.event":
tBuffer.add(externalModel);
addedModels.add(externalModel);
break;
default:
break;
}
}
}
TreeSet<String> checkedWorkspace = new TreeSet<>();
IPluginModelBase[] workspaceModels = PluginRegistry.getWorkspaceModels();
for (IPluginModelBase workspaceModel : workspaceModels) {
checkedWorkspace.add(workspaceModel.getPluginBase().getId());
}
EclipsePluginValidationOperation eclipsePluginValidationOperation = new EclipsePluginValidationOperation(
configuration);
eclipsePluginValidationOperation.run(null);
while (eclipsePluginValidationOperation.hasErrors()) {
Set<String> additionalIds = DependencyManager.getDependencies(addedModels.toArray(), true, null);
if (additionalIds.isEmpty()) {
break;
}
additionalIds.stream().map(PluginRegistry::findEntry).filter(Objects::nonNull).map(ModelEntry::getModel)
.forEach(addedModels::add);
for (String id : additionalIds) {
IPluginModelBase plugin = findPlugin(id);
if (checkedWorkspace.contains(plugin.getPluginBase().getId())
&& (!plugin.getPluginBase().getId().endsWith("tests"))) {
wBuffer.add(plugin);
} else {
tBuffer.add(plugin);
}
}
eclipsePluginValidationOperation.run(null);
}
configuration.setAttribute(IPDELauncherConstants.SELECTED_WORKSPACE_PLUGINS, wBuffer.toString());
configuration.setAttribute(IPDELauncherConstants.SELECTED_TARGET_PLUGINS, tBuffer.toString());
}
protected IPluginModelBase findPlugin(final String id) {
ModelEntry entry = PluginRegistry.findEntry(id);
if (entry != null) {
return entry.getModel();
}
return null;
}
}

Ideablade's Cocktail Composition Container for WCF projects

I recently upgraded an application I am working on from Cocktail 1.4 to Cocktail 2.6 (Punch). I have adjusted my bootstrapper class for the wpf project which now loads with no issues. However, on my WCF / Web projects, I am receiving a runtime exception with the following error when attempting to call Composition.GetInstance:
"You must first set a valid CompositionProvider by using Composition.SetProvider."
After digging into the issue a bit, it appears the composition container is automatically configured when your bootstrapper inherits from CocktailMefBootstrapper. I currently do not have bootstrapper classes at all for non-wpf projects. Prior to the upgrade, all I had to do was call the configure method on the Composition class to configure the composition container, but it appears that it has been deprecated:
Composition.Configure();
I noticed that you can also call Composition.SetProvider(), however I am a little unsure on how to satisfy the method signature exactly. The DevForce Punch documentation states that the generic type for the bootstrapper class should be a viewmodel, and there are no views / view models in a service project. This leaves me in limbo on what to do as I don't want to rip cocktail out of these WCF projects. Is there still a way to use Cocktail's composition container without a bootstrapper for a project in Cocktail (Punch) 2.6?
UPDATE
I found this on the DevForce forums. So it appears that I ought to learn how to configure a multi threaded ICompositionProvider and call Composition.SetProvider() as mentioned above. Any recommended articles to achieving this?
After digging through Punch's source code and looking at Ideablade's MefCompositionContainer, which implements ICompositionProvider, I created my own thread safe implementation of ICompositionProvider. Below is the code I used. Basically, it's the same code for Ideablade's MefCompositionContainer which can be found here in their repository. The only change is that I am passing a bool flag of true into the CompositionContainer's constructor. MSDN lists the pros and cons of making the container thread safe
internal partial class ThreadSafeCompositionProvider : ICompositionProvider
{
static ThreadSafeCompositionProvider()
{
CompositionHost.IgnorePatterns.Add("Caliburn.Micro*");
CompositionHost.IgnorePatterns.Add("Windows.UI.Interactivity*");
CompositionHost.IgnorePatterns.Add("Cocktail.Utils*");
CompositionHost.IgnorePatterns.Add("Cocktail.Compat*");
CompositionHost.IgnorePatterns.Add("Cocktail.dll");
CompositionHost.IgnorePatterns.Add("Cocktail.SL.dll");
CompositionHost.IgnorePatterns.Add("Cocktail.WinRT.dll");
}
public IEnumerable<Assembly> GetProbeAssemblies()
{
IEnumerable<Assembly> probeAssemblies = CompositionHost.Instance.ProbeAssemblies;
var t = GetType();
// Add Cocktail assembly
probeAssemblies = probeAssemblies.Concat(GetType().GetAssembly());
return probeAssemblies.Distinct(x => x);
}
private List<Assembly> _probeAssemblies;
private AggregateCatalog _defaultCatalog;
private ComposablePartCatalog _catalog;
private CompositionContainer _container;
public ComposablePartCatalog Catalog
{
get { return _catalog ?? DefaultCatalog; }
}
public ComposablePartCatalog DefaultCatalog
{
get
{
if (_defaultCatalog == null)
{
_probeAssemblies = GetProbeAssemblies().ToList();
var mainCatalog = new AggregateCatalog(_probeAssemblies.Select(x => new AssemblyCatalog(x)));
_defaultCatalog = new AggregateCatalog(mainCatalog);
CompositionHost.Recomposed += new EventHandler<RecomposedEventArgs>(OnRecomposed)
.MakeWeak(x => CompositionHost.Recomposed -= x);
}
return _defaultCatalog;
}
}
internal void OnRecomposed(object sender, RecomposedEventArgs args)
{
if (args.HasError) return;
var newAssemblies = GetProbeAssemblies()
.Where(x => !_probeAssemblies.Contains(x))
.ToList();
if (newAssemblies.Any())
{
var catalog = new AggregateCatalog(newAssemblies.Select(x => new AssemblyCatalog(x)));
_defaultCatalog.Catalogs.Add(catalog);
_probeAssemblies.AddRange(newAssemblies);
}
// Notify clients of the recomposition
var handlers = Recomposed;
if (handlers != null)
handlers(sender, args);
}
public CompositionContainer Container
{
get { return _container ?? (_container = new CompositionContainer(Catalog, true)); }
}
public Lazy<T> GetInstance<T>() where T : class
{
var exports = GetExportsCore(typeof(T), null).ToList();
if (!exports.Any())
throw new Exception(string.Format("Could Not Locate Any Instances Of Contract", typeof(T).FullName));
return new Lazy<T>(() => (T)exports.First().Value);
}
public T TryGetInstance<T>() where T : class
{
if (!IsTypeRegistered<T>())
return null;
return GetInstance<T>().Value;
}
public IEnumerable<T> GetInstances<T>() where T : class
{
var exports = GetExportsCore(typeof(T), null);
return exports.Select(x => (T)x.Value);
}
public Lazy<object> GetInstance(Type serviceType, string contractName)
{
var exports = GetExportsCore(serviceType, contractName).ToList();
if (!exports.Any())
throw new Exception(string.Format("Could Not Locate Any Instances Of Contract",
serviceType != null ? serviceType.ToString() : contractName));
return new Lazy<object>(() => exports.First().Value);
}
public object TryGetInstance(Type serviceType, string contractName)
{
var exports = GetExportsCore(serviceType, contractName).ToList();
if (!exports.Any())
return null;
return exports.First().Value;
}
public IEnumerable<object> GetInstances(Type serviceType, string contractName)
{
var exports = GetExportsCore(serviceType, contractName);
return exports.Select(x => x.Value);
}
public ICompositionFactory<T> GetInstanceFactory<T>() where T : class
{
var factory = new ThreadSafeCompositionFactory<T>();
Container.SatisfyImportsOnce(factory);
if (factory.ExportFactory == null)
throw new CompositionException(string.Format("No export found.", typeof(T)));
return factory;
}
public ICompositionFactory<T> TryGetInstanceFactory<T>() where T : class
{
var factory = new ThreadSafeCompositionFactory<T>();
Container.SatisfyImportsOnce(factory);
if (factory.ExportFactory == null)
return null;
return factory;
}
public void BuildUp(object instance)
{
// Skip if in design mode.
if (DesignTime.InDesignMode())
return;
Container.SatisfyImportsOnce(instance);
}
public bool IsRecomposing { get; internal set; }
public event EventHandler<RecomposedEventArgs> Recomposed;
internal bool IsTypeRegistered<T>() where T : class
{
return Container.GetExports<T>().Any();
}
public void Configure(CompositionBatch compositionBatch = null, ComposablePartCatalog catalog = null)
{
_catalog = catalog;
var batch = compositionBatch ?? new CompositionBatch();
if (!IsTypeRegistered<IEventAggregator>())
batch.AddExportedValue<IEventAggregator>(new EventAggregator());
Compose(batch);
}
public void Compose(CompositionBatch compositionBatch)
{
if (compositionBatch == null)
throw new ArgumentNullException("compositionBatch");
Container.Compose(compositionBatch);
}
private IEnumerable<Lazy<object>> GetExportsCore(Type serviceType, string key)
{
return Container.GetExports(serviceType, null, key);
}
}
After setting up that class, I added a configuration during startup to instantiate my new thread safe composition provider and to set it as the provider for Punch's Composition class:
if (createThreadSafeCompositionContainer)
{
var threadSafeContainer = new ThreadSafeCompositionProvider();
Composition.SetProvider(threadSafeContainer);
}
Seems to be working like a charm!

How to get the project when right-click on a project/file/others in an eclipse-plugin

I'm write a simple eclipse plugin, but have a problem: When user right-click on a node(maybe a project, a file, a java compilation unit, or others), I want to get the project it belongs.
The sample code is:
public class MyAction implements IObjectActionDelegate {
private IProject project;
public void selectionChanged(IAction action, ISelection selection) {
this.project = getSelectedProject(selection);
}
public static IProject getSelectedProject(Object obj) throws Exception {
if (obj == null) {
return null;
}
if (obj instanceof IResource) {
return ((IResource) obj).getProject();
} else if (obj instanceof IStructuredSelection) {
return getSelectedProject(((IStructuredSelection) obj).getFirstElement());
}
return null;
}
}
It works at most of time, but sometimes, for example, I right-clicked on a java file, the selection will be a ICompilationUnit. Although I can add one more if in the getSelectedProject, but I don't think it's a good idea.
Is there a way to get the project of selected objects nomatter what have been selected? I don't want to add them one by one.
ICompilationUnit extends IAdaptable (see http://publib.boulder.ibm.com/infocenter/rsmhelp/v7r0m0/index.jsp?topic=/org.eclipse.jdt.doc.isv/reference/api/org/eclipse/jdt/core/ICompilationUnit.html)
You can try and use the IAdaptable interface like that:
if (obj instanceof IAdaptable) {
IResource res = (IResource)(((IAdaptable)obj).getAdapter(IResource.class));
if (res != null) {
return res.getProject();
}
}
There are no way to convert an ICompilationUnit, IPackage, or whatever, to an IResource as there are most often no corresponding resource! E.g. for the .class elements in the navigator, the element corresponds to an entry in a JAR file or in a dependency plug-in from the target platform.
it up answer don't work, may it should be:
if (obj instanceof IStructuredSelection) {
IStructuredSelection selection1 = (IStructuredSelection)obj;
Object element = selection1.getFirstElement();
IProject project = null;
if (element instanceof IProject) {
project = (IProject) element;
} else if (element instanceof IAdaptable) {
project = (IProject) ((IAdaptable) element).getAdapter(IProject.class);
}
if (project != null) {
return project;
}
}