Informar de la instalación de la aplicación Android de nuevo a facebook sin usar su api

Desde mi aplicación de Android, me gustaría publicar su instalación de nuevo en facebook para permitir el seguimiento de conversiones para sus anuncios de instalación de aplicaciones para móviles, pero me gustaría hacerlo sin usar su api.

Así que en lugar de hacer

com.facebook.Settings.publishInstall(context, appId); 

Me gustaría enviar una solicitud HTTP con los parámetros necesarios a alguna URL.

EDITAR:

He registrado las dos solicitudes que se envían a facebook para publicar la instalación de la aplicación y se ven así:

Solicitud:

 GET /[app id]?format=json&sdk=android&fields=supports_attribution HTTP/1.1 User-Agent: FBAndroidSDK.3.0.0.b Content-Type: multipart/form-data; boundary=3i2ndDfv2rTHiSisAbouNdArYfORhtTPEefj3q2f Host: graph.facebook.com Connection: Keep-Alive Accept-Encoding: gzip 

Respuesta:

 HTTP/1.1 200 OK Access-Control-Allow-Origin: * Cache-Control: private, no-cache, no-store, must-revalidate Content-Type: text/javascript; charset=UTF-8 ETag: "24ea6554744eece05b90dd2e65af63277cdcaf53" Expires: Sat, 01 Jan 2000 00:00:00 GMT Pragma: no-cache X-FB-Rev: 658994 X-FB-Debug: P2GE3fDVAnRJh62rBS5WXD4ce1hTy8Pwvjq5rT/I+TI= Date: Tue, 30 Oct 2012 11:37:09 GMT Connection: keep-alive Content-Length: 52 {"supports_attribution":true,"id":"[app id]"} 

Solicitud:

 POST /[app id]/activities?format=json&sdk=android&migration_bundle=fbsdk%3A20120913 HTTP/1.1 User-Agent: FBAndroidSDK.3.0.0.b Content-Type: multipart/form-data; boundary=3i2ndDfv2rTHiSisAbouNdArYfORhtTPEefj3q2f Host: graph.facebook.com Connection: Keep-Alive Transfer-Encoding: chunked Accept-Encoding: gzip 261 --3i2ndDfv2rTHiSisAbouNdArYfORhtTPEefj3q2f Content-Disposition: form-data; name="format" json --3i2ndDfv2rTHiSisAbouNdArYfORhtTPEefj3q2f Content-Disposition: form-data; name="sdk" android --3i2ndDfv2rTHiSisAbouNdArYfORhtTPEefj3q2f Content-Disposition: form-data; name="migration_bundle" fbsdk:20120913 --3i2ndDfv2rTHiSisAbouNdArYfORhtTPEefj3q2f Content-Disposition: form-data; name="attribution" ab175007-2725-464f-a111-b8b1a92bf1dd --3i2ndDfv2rTHiSisAbouNdArYfORhtTPEefj3q2f Content-Disposition: form-data; name="event" MOBILE_APP_INSTALL --3i2ndDfv2rTHiSisAbouNdArYfORhtTPEefj3q2f 0 

Respuesta:

 HTTP/1.1 200 OK Access-Control-Allow-Origin: * Cache-Control: private, no-cache, no-store, must-revalidate Content-Type: text/javascript; charset=UTF-8 Expires: Sat, 01 Jan 2000 00:00:00 GMT Pragma: no-cache X-FB-Rev: 658994 X-FB-Debug: +0GWQ4cu+tFeAg3QEuwYGx+HAt7t37itzxEYBaTZF8U= Date: Tue, 30 Oct 2012 11:38:33 GMT Connection: keep-alive Content-Length: 4 true 

He incluido una versión reducida de la api de Facebook en mi aplicación que no puede hacer nada más, pero simplemente envíe esas dos solicitudes. Lo probaré e informará sobre cómo funciona.

De manera óptima, me gustaría enviar las solicitudes desde un servidor y no desde el teléfono en absoluto.

Usted puede hacer esto con llamada simple

 FacebookHelper.appInstall(this.getApplicationContext(), "<com.your.package>", "<your facebook app id>"); 

Y la biblioteca a continuación.

Recuerda que solo puedes realizar el seguimiento de la aplicación si la aplicación de facebook está instalada; entonces tienes attributionId. Si desea enviar esta solicitud en el servidor, tiene que enviar atributionId a su servidor.

 import android.content.ContentResolver; import android.content.Context; import android.database.Cursor; import android.net.Uri; import org.apache.http.HttpResponse; import org.apache.http.HttpStatus; import org.apache.http.client.HttpClient; import org.apache.http.client.methods.HttpEntityEnclosingRequestBase; import org.apache.http.client.methods.HttpPost; import org.apache.http.client.methods.HttpRequestBase; import org.apache.http.entity.mime.HttpMultipartMode; import org.apache.http.entity.mime.MultipartEntity; import org.apache.http.entity.mime.content.StringBody; import org.apache.http.impl.client.DefaultHttpClient; import org.apache.http.protocol.HTTP; import java.io.IOException; import java.nio.charset.Charset; import static com.google.common.base.Preconditions.checkArgument; import static com.google.common.base.Preconditions.checkNotNull; public class FacebookHelper { private static final Uri ATTRIBUTION_ID_CONTENT_URI = Uri.parse("content://com.facebook.katana.provider.AttributionIdProvider"); private static final String ATTRIBUTION_ID_COLUMN_NAME = "aid"; private static final String USER_AGENT = "FBAndroidSDK/3.5.0"; private final DefaultHttpClient mHttpClient; private final String mApplicationPackage; private final String mApplicationId; private FacebookHelper(String applicationPackage, String applicationId) { checkNotNull(applicationPackage); checkNotNull(applicationId); mApplicationPackage = applicationPackage; mApplicationId = applicationId; mHttpClient = new DefaultHttpClient(); } private static String getAttributionId(ContentResolver cr) { checkNotNull(cr); final String [] projection = {ATTRIBUTION_ID_COLUMN_NAME}; final Cursor cursor = cr.query(ATTRIBUTION_ID_CONTENT_URI, projection, null, null, null); if (cursor == null) { return null; } try { if (!cursor.moveToFirst()) { return null; } final int attributionColumnIndex = cursor.getColumnIndex(ATTRIBUTION_ID_COLUMN_NAME); if (attributionColumnIndex < 0) { return null; } return cursor.getString(attributionColumnIndex); } finally { cursor.close(); } } public static void appInstall(Context applicationContext, String applicationPackage, String applicationId) throws IOException { checkNotNull(applicationContext); checkNotNull(applicationPackage); checkNotNull(applicationId); final ContentResolver cr = applicationContext.getContentResolver(); final String attributionId = getAttributionId(cr); if (attributionId == null) { // we can not send anything if facebook app is not installed return; } final FacebookHelper facebookHelper = new FacebookHelper(applicationPackage, applicationId); facebookHelper.appInstall(attributionId); } private void appInstall(String attribution) throws IOException { checkNotNull(attribution); String url = String.format("https://graph.facebook.com/%s/activities", mApplicationId); MultipartEntity entity = new MultipartEntity( HttpMultipartMode.BROWSER_COMPATIBLE); Charset charset = Charset.forName(HTTP.UTF_8); entity.addPart("sdk", new StringBody("android", charset)); entity.addPart("format", new StringBody("json", charset)); entity.addPart("event", new StringBody("MOBILE_APP_INSTALL", charset)); entity.addPart("attribution", new StringBody(attribution, charset)); entity.addPart("auto_publish", new StringBody("false", charset)); entity.addPart("application_tracking_enabled", new StringBody("true", charset)); entity.addPart("migration_bundle", new StringBody("fbsdk:20130708", charset)); entity.addPart("application_package_name", new StringBody(mApplicationPackage, charset)); HttpEntityEnclosingRequestBase request = new HttpPost(url); setupDefaultHeaders(request); request.setEntity(entity); HttpResponse response = getHttpClient().execute(request); validateResponseCode(response, HttpStatus.SC_OK); } private void validateResponseCode(HttpResponse response, int expectedStatusCode) throws IOException { checkNotNull(response); checkArgument(expectedStatusCode != HttpStatus.SC_UNPROCESSABLE_ENTITY); checkArgument(expectedStatusCode != HttpStatus.SC_NOT_FOUND); int statusCode = response.getStatusLine().getStatusCode(); if (statusCode != expectedStatusCode) { throw new IOException("Wrong response code: "+ "expected <" +expectedStatusCode +"> was <" +statusCode+">"); } } private HttpClient getHttpClient() { return mHttpClient; } private void setupDefaultHeaders(HttpRequestBase request) { checkNotNull(request); request.setHeader("Accept", "application/json"); request.setHeader("User-Agent", USER_AGENT); } } 

Esta biblioteca utiliza guayaba checkArgument y checkNotNull si no usas guayaba solo puedes saltar esas líneas.

No es posible hacerlo sin integrar nuestro SDK. Para los anuncios de instalación de aplicaciones, el SDK debe estar integrado con tu aplicación. Si vas al panel de control de la aplicación> Promocionar> Feed de Android, hay un mensaje que indica:

Nota: esto solo es efectivo si integraste el SDK de Facebook para Android. Se te cobrará cada vez que alguien vea tu anuncio.

Terminé publicando la instalación de nuevo a facebook desde mi aplicación, usando esta versión despojada de su api:

 package de.techunity.fancy.facebook.publishinstall; import org.json.JSONException; import android.content.ContentResolver; import android.content.Context; import android.content.SharedPreferences; import android.database.Cursor; import android.net.Uri; import android.os.Bundle; import android.util.Log; import com.facebook.android.Util; public class InstallPublisher { private static final Uri ATTRIBUTION_ID_CONTENT_URI = Uri.parse("content://com.facebook.katana.provider.AttributionIdProvider"); private static final String ATTRIBUTION_ID_COLUMN_NAME = "aid"; private static final String ATTRIBUTION_PREFERENCES = "com.facebook.sdk.attributionTracking"; private static final String PUBLISH_ACTIVITY_PATH = "%s/activities"; private static final String MOBILE_INSTALL_EVENT = "MOBILE_APP_INSTALL"; private static final String SUPPORTS_ATTRIBUTION = "supports_attribution"; private static final String APPLICATION_FIELDS = "fields"; private static final String ANALYTICS_EVENT = "event"; private static final String ATTRIBUTION_KEY = "attribution"; /** * Manually publish install attribution to the facebook graph. Internally handles tracking repeat calls to prevent * multiple installs being published to the graph. * @param context * @return returns false on error. Applications should retry until true is returned. Safe to call again after * true is returned. */ public static boolean publishInstall(final Context context, final String applicationId) { try { if (applicationId == null) { return false; } final String attributionId = InstallPublisher.getAttributionId(context.getContentResolver()); final SharedPreferences preferences = context.getSharedPreferences(ATTRIBUTION_PREFERENCES, Context.MODE_PRIVATE); final String pingKey = applicationId+"ping"; long lastPing = preferences.getLong(pingKey, 0); if (lastPing == 0 && attributionId != null) { new Thread(new Runnable() { @Override public void run() { try { Bundle supportsAttributionParams = new Bundle(); supportsAttributionParams.putString(APPLICATION_FIELDS, SUPPORTS_ATTRIBUTION); Request pingRequest = Request.newGraphPathRequest(applicationId, null); pingRequest.setParameters(supportsAttributionParams); GraphObject supportResponse = pingRequest.executeAndWait().getGraphObject(); Object doesSupportAttribution = supportResponse.getProperty(SUPPORTS_ATTRIBUTION); if (!(doesSupportAttribution instanceof Boolean)) { throw new JSONException(String.format( "%s contains %s instead of a Boolean", SUPPORTS_ATTRIBUTION, doesSupportAttribution)); } if ((Boolean)doesSupportAttribution) { GraphObject publishParams = (GraphObject) GraphObjectWrapper.createGraphObject(); publishParams.setProperty(ANALYTICS_EVENT, MOBILE_INSTALL_EVENT); publishParams.setProperty(ATTRIBUTION_KEY, attributionId); String publishUrl = String.format(PUBLISH_ACTIVITY_PATH, applicationId); Request publishRequest = Request.newPostRequest(publishUrl, publishParams, null); publishRequest.executeAndWait(); // denote success since no error threw from the post. SharedPreferences.Editor editor = preferences.edit(); editor.putLong(pingKey, System.currentTimeMillis()); editor.commit(); } } catch (Exception e) { Log.d("fancy", "Couldn't publish publish install to facebook", e); } finally { Log.d("fancy", "Publish install to facebook thread completed"); } } }, "facebook publish install thread").start(); } return true; } catch (Exception e) { // if there was an error, fall through to the failure case. Util.logd("Facebook-publish", e.getMessage()); } return false; } public static String getAttributionId(ContentResolver contentResolver) { String [] projection = {ATTRIBUTION_ID_COLUMN_NAME}; Cursor c = contentResolver.query(ATTRIBUTION_ID_CONTENT_URI, projection, null, null, null); if (c == null || !c.moveToFirst()) { return null; } String attributionId = c.getString(c.getColumnIndex(ATTRIBUTION_ID_COLUMN_NAME)); c.close(); return attributionId; } } 
  • NPE en Facebook SDK 4.10: Intenta invocar el método de interfaz 'java.lang.Object com.facebook.inject.Lazy.get ()' en una referencia de objeto nulo
  • Android: ¿Cuál es la clase de diálogo compartido en Facebook SDK 4.x
  • ¿Cómo puedo convertir la entrada de Facebook created_time a la zona horaria del usuario?
  • El inicio de sesión de API de Facebook falla con la aplicación FB instalada en el teléfono
  • Realizar solicitudes REST autorizadas (a través de facebook) a mi servidor node.js en una aplicación PhoneGap
  • Texto de recorte de Facebook en Android cuando se usa una intención de ACTION_SEND
  • ClassNotFoundException en la apertura de icono de compartir facebook en android
  • Una biblioteca utiliza el mismo paquete que este proyecto después de importar Facebook SDK
  • Facebook SDK en Android: invalidar u ocultar el diálogo de progreso cuando inicie sesión
  • ¿Qué es el "Nombre de clase de Android" para una aplicación de Facebook escrita en Flex?
  • Session.StatusCallback no se puede resolver con un tipo - Facebook API
  • FlipAndroid es un fan de Google para Android, Todo sobre Android Phones, Android Wear, Android Dev y Aplicaciones para Android Aplicaciones.