Skip to content

Instantly share code, notes, and snippets.

@showsky
Last active April 1, 2022 07:24
Show Gist options
  • Select an option

  • Save showsky/6b3f04675edf3b9b3a84aff834a5dd37 to your computer and use it in GitHub Desktop.

Select an option

Save showsky/6b3f04675edf3b9b3a84aff834a5dd37 to your computer and use it in GitHub Desktop.

Sitemaji SDK (v1.12.3)

Download

Download as a gradle dependency in your project. To use it you will have to edit your gradle files in two places. First you need to add new maven repository to your top level gradle file. The repository is a link to your GitHub repository created in step one. Here's what you need to add to use SitemajiSDK library:

...

repositories {
    maven { url 'https://thefirstweb.github.io/repo/' }
    maven { url 'https://sdk.tapjoy.com/" }
    maven { url 'https://dl.bintray.com/vpon-sdk/maven' }
    maven { url 'https://m.vpon.com/sdk/android/maven' }
    maven { url 'https://dl-maven-android.mintegral.com/repository/mbridge_android_sdk_oversea' }
}

...

dependencies {
    // dependencies sitemaji library
    implementation 'com.google.android.gms:play-services-ads:20.6.0'
    implementation 'com.sitemaji.sdk:sitemaji:1.12.3@aar'
    
    // dependencies inmobi library
    implementation 'com.android.support:recyclerview-v7:28.0.0'
    implementation 'com.squareup.picasso:picasso:2.71828'
    
    // mobvista
    implementation 'com.mbridge.msdk.oversea:mbnative:15.7.41'
    implementation 'com.mbridge.msdk.oversea:mbnativeadvanced:15.7.41'
}

...
  • Third-party library
provider name package name require
google com.google.android.gms:play-services-ads:20.6.0 Y
mobvista com.mbridge.msdk.oversea:mbnative:15.7.41 N
hayzap N
tayjoy com.tapjoy:tapjoy-android-sdk:12.8.1 N
inmobi com.inmobi.monetization:inmobi-ads:10.0.3 N
sitemaji com.sitemaji.sdk:sitemaji:1.12.3@aar Y
vpon com.vpon:vpadnSDK:5.3.0 N
vungle com.vungle:publisher-sdk-android:6.10.5 N
unity com.unity3d.ads:unity-ads:3.7.5 N
applovin com.applovin:applovin-sdk:11.2.2 N

Support Ad

provider name banner interstitial interstitial video video rewared video native webview
hayzap
admod V
mobvista V
tapjoy V
inmobi V
sitemaji V
vungle V V V
unity V V
applovin V

Env

  • com.android.tools.build:gradle:7.1.2
  • minSdkVersion 19

Proguard

  • Sitemaji Core

     -keep class com.sitemaji.** {*; }
     -dontwarn com.sitemaji.**
    
  • Tapjoy

    -keep class com.tapjoy.** { *; }
    -keep class com.moat.** { *; }
    -keepattributes JavascriptInterface
    -keepattributes *Annotation*
    -keep class * extends java.util.ListResourceBundle {
    protected Object[][] getContents();
    }
    -keep public class com.google.android.gms.common.internal.safeparcel.SafeParcelable {
    public static final *** NULL;
    }
    -keepnames @com.google.android.gms.common.annotation.KeepName class *
    -keepclassmembernames class * {
    @com.google.android.gms.common.annotation.KeepName *;
    }
    -keepnames class * implements android.os.Parcelable {
    public static final ** CREATOR;
    }
    -keep class com.google.android.gms.ads.identifier.** { *; }
    -dontwarn com.tapjoy.**
    
  • Vpon

    -dontwarn c.**
    -dontwarn com.vpon.**
    -dontwarn vpadn.**
    -keep class c.**{ *; }
    -keep class com.vpon.** { *; }
    -keep class vpon.** { *; }
    -keep class com.vpadn.** { *; }
    -keep class vpadn.** { *; }
    
  • Vungle

    -dontwarn com.vungle.warren.downloader.DownloadRequestMediator$Status
    -dontwarn com.vungle.warren.error.VungleError$ErrorCode
    
  • Mobvista

    -keepattributes Signature   
    -keepattributes *Annotation*   
    -keep class com.mbridge.** {*; }  
    -keep interface com.mbridge.** {*; }  
    -keep interface androidx.** { *; }
    -keep class androidx.** { *; }
    -keep public class * extends androidx.** { *; }
    -dontwarn com.mbridge.**   
    -keep class **.R$* { public static final int mbridge*; }
    

Usage

First you apply for [PACKAGE_HASH]

need put SitemajiCore init to application, it async to server fetch config

  • you can use SitemajiCoreStatusListener() Listener status

     public class App extends Application {
     
         private final static String PACKAGE_HASH = "xxx";
     
         @Override
         public void onCreat() {
             super.onCreate();
             new SitemajiCore.Builder(this, PACKAGE_HASH)
                 .withDevelopEnable(false)
                 .withLogEnabled(false)
                 .withTestDevice("DD7DB6C775D03811F15BE3E2756BB023")    // Gogole Advertising ID
                 .withCoreStatusListener(new SitemajiCoreStatusListener() {
                     @Override
                     public void onSuccess() {
                         Log.i(TAG, "onSuccess");
                     }
     
                     @Override
                     public void onFail(int i, String s) {
                         Log.i(TAG, "onFail erroNo: " + i + " errorMessage: " + s);
                     }
                 })
                 .build();
         }
     }
  • you can check SitemajiCore init status

     SitemajiCore.getInstanct().isInitConfig();
  • Sitemaji class

     SitemajiCore.Builder()
  • SitemajiCoreStatusListener interface

     public interface SitemajiCoreStatusListener {
     
         public void onSuccess();
         public void onFail(int errorNo, String errorMessage);
     }

Banner

First new SitemajiBanner() then use fetch() , it async to server fetch ad rule data, next call display() attached video layout.

public class BannerActivity extends Activity {

    private final static String TAG = BannerActivity.class.getSimpleName();
    private Context mContext;
    private SitemajiBanner mSitemajiBanner;

    @Override
    protected void onCreate(@Nullable Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        mContext = this;
        setContentView(R.layout.activity_banner);
        initView();
    }

    private void initView() {
        findViewById(R.id.button_banner).setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                initBanner();
            }
        });
    }

    private void initBanner() {
        mSitemajiBanner = new SitemajiBanner();
        mSitemajiBanner.setBannerListener(new BannerListener() {
            @Override
            public void onClick() {
                Log.d(TAG, "onClick");
            }

            @Override
            public void onClose() {
                Log.d(TAG, "onClose");
            }

            @Override
            public void onLoaded() {
                Log.d(TAG, "onLoaded");
            }

            @Override
            public void onLoadFail() {
                Log.d(TAG, "onLoadFail");
            }

            @Override
            public void onFail(int errorNo, String errorMessage) {
                Log.d(TAG, "onFail");
            }
        });
        mSitemajiBanner.fetch(this, new SitemajiAdFetchListener() {
            @Override
            public void onSuccess() {
                LinearLayout.LayoutParams layoutParams = new LinearLayout.LayoutParams(
                    LinearLayout.LayoutParams.WRAP_CONTENT,
                    LinearLayout.LayoutParams.WRAP_CONTENT
                );
                layoutParams.gravity = Gravity.CENTER;
                mSitemajiBanner.display(
                    BannerActivity.this,
                    (ViewGroup) findViewById(R.id.linearLayout),
                    layoutParams
                );
            }

            @Override
            public void onFail(int errorNo, String errorMessage) {
                Log.d(TAG, String.format("Banner onFail errorNo: %s errorMessage: %s", errorNo, errorMessage));
            }
        });
    }

    @Override
    protected void onDestroy() {
        super.onDestroy();
        
        //  Don't forget destroy
        if (mSitemajiBanner != null) {
            mSitemajiBanner.onDestroy();
        }
    }
}
  • BannerSitemaji

     SitemajiBanner.setBannerListener(BannerListener bannerListener)
     SitemajiBanner.fetch(@NonNull Activity activity, @NonNull SitemajiAdFetchListener sitemajiAdFetchListener)
     SitemajiBanner.display(@NonNull Activity activity, @NonNull ViewGroup rootView, ViewGroup.LayoutParams params)
     SitemajiBanner.display(Activity activity)
    
  • BannerListener

     public interface BannerListener {
         public void onClick();
         public void onClose();
         public void onLoaded();
         public void onLoadFail();
         public void onFail(int errorNo, String errorMessage);
     }
    

Interstitial

First new SitemajiInterstitial() then use fetch() , it async to server fetch ad rule data, next call display() attached video layout.

public class SitemajiActivity extends Activity {

    private final static String TAG = SitemajiActivity.class.getSimpleName();
    private SitemajiInterstitial mSitemajiInterstitial;
    
    protected void onCreate(@Nullable Bundle savedInstanceState) {
        super.onCreat(savedInstanceState)
        
        initSitemajiView()
    }
    
    private void initSitemajiView() {
        mSitemajiInterstitial = new SitemajiInterstitial();
        mSitemajiInterstitial.setProviderStatusListener(new ProviderStatusListener() {
            @Override
            public void onProviderStatus(String provider, String status) {
                Log.d(TAG, provider + " : " + status);
            }
        });
        mSitemajiInterstitial.setInterstitialListener(new InterstitialListener() {
            @Override
            public void onShow() {
                Log.d(TAG, "onClick");
            }
        
            @Override
            public void onClick() {
                Log.d(TAG, "onClick");
            }

            @Override
            public void onClose() {
                Log.d(TAG, "onClose");
            }

            @Override
            public void onLoaded() {
                Log.d(TAG, "onLoaded");
            }

            @Override
            public void onLoadFail() {
                Log.d(TAG, "onLoadFail");
            }

            @Override
            public void onFail(int errorNo, String errorMessage) {
                Log.d(TAG, "onFail");
            }
        });
        
        mSitemajiInterstitial.fetch(MainActivity.this, new SitemajiAdFetchListener() {
            @Override
            public void onSuccess() {
                Log.d(TAG, "Interstitial onSuccess");
                mSitemajiInterstitial.display(MainActivity.this);
            }
    
            @Override
            public void onFail(int errorNo, String errorMessage) {
                Log.d(TAG, String.format("Interstitial onFail errorNo: %s errorMessage: %s", errorNo, errorMessage));
            }
        });
    }        
    
    @Override
    protected void onDestroy() {
        super.onDestroy();
        
        //  Don't forget destroy
        if (mSitemajiInterstitial != null) {
            mSitemajiInterstitial.onDestroy();
        {
    }
}
  • SitemajiInterstitial class

     SitemajiInterstitial.setInterstitialListener(InterstitialListener interstitialListener)
     SitemajiInterstitial.fetch(Activity activity, @NonNull SitemajiAdFetchListener sitemajiAdFetchListener)
     SitemajiInterstitial.fetch(Activity activity, String provider, @NonNull SitemajiAdFetchListener sitemajiAdFetchListener)
     SitemajiInterstitial.display(Activity activity)
  • InterstitialListener interface

    public interface InterstitialListener {
        public void onShow():
        public void onClick();
        public void onClose();
        public void onLoaded();
        public void onLoadFail();
        public void onFail(int errorNo, String errorMessage);
    }
    

Interstitial Video

First new SitemajiInterstitialVideo() then use fetch() , it async to server fetch ad rule data, next call display() attached video layout.

public class SitemajiActivity extends Activity {

    private final static String TAG = SitemajiActivity.class.getSimpleName();
    private SitemajiInterstitialVideo mSitemajiInterstitialVideo;
    
    protected void onCreate(@Nullable Bundle savedInstanceState) {
        super.onCreat(savedInstanceState)
        
        initSitemajiView()
    }
    
    private void initSitemajiView() {
        mSitemajiInterstitialVideo = new SitemajiInterstitialVideo();
        mSitemajiInterstitialVideo.setProviderStatusListener(new ProviderStatusListener() {
            @Override
            public void onProviderStatus(String provider, String status) {
                Log.d(TAG, provider + " : " + status);
            }
        });
        mSitemajiInterstitialVideo.setInterstitialListener(new InterstitialListener() {
            @Override
            public void onShow() {
                Log.d(TAG, "onClick");
            }
        
            @Override
            public void onClick() {
                Log.d(TAG, "onClick");
            }

            @Override
            public void onClose() {
                Log.d(TAG, "onClose");
            }

            @Override
            public void onLoaded() {
                Log.d(TAG, "onLoaded");
            }

            @Override
            public void onLoadFail() {
                Log.d(TAG, "onLoadFail");
            }

            @Override
            public void onFail(int errorNo, String errorMessage) {
                Log.d(TAG, "onFail");
            }
        });
        
        mSitemajiInterstitialVideo.fetch(MainActivity.this, new SitemajiAdFetchListener() {
            @Override
            public void onSuccess() {
                Log.d(TAG, "Interstitial onSuccess");
                mSitemajiInterstitialVideo.display(MainActivity.this);
            }
    
            @Override
            public void onFail(int errorNo, String errorMessage) {
                Log.d(TAG, String.format("Interstitial onFail errorNo: %s errorMessage: %s", errorNo, errorMessage));
            }
        });
    }        
    
    @Override
    protected void onDestroy() {
        super.onDestroy();
        
        //  Don't forget destroy
        if (mSitemajiInterstitialVideo != null) {
            mSitemajiInterstitialVideo.onDestroy();
        {
    }
}
  • SitemajiInterstitial class

     SitemajiInterstitial.setInterstitialListener(InterstitialListener interstitialListener)
     SitemajiInterstitial.fetch(Activity activity, @NonNull SitemajiAdFetchListener sitemajiAdFetchListener)
     SitemajiInterstitial.fetch(Activity activity, String provider, @NonNull SitemajiAdFetchListener sitemajiAdFetchListener)
     SitemajiInterstitial.display(Activity activity)
  • InterstitialListener interface

    public interface InterstitialListener {
        public void onShow():
        public void onClick();
        public void onClose();
        public void onLoaded();
        public void onLoadFail();
        public void onFail(int errorNo, String errorMessage);
    }
    

Native

First new SitemajiBanner() then use fetch() , it async to server fetch ad rule data, next call display() attached ViewGroup layout.

public class NativeActivity extends Activity {

    private final static String TAG = NativeActivity.class.getSimpleName();
    private Context mContext;
    private SitemajiNative mSitemajiNative;

    @Override
    protected void onCreate(@Nullable Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        mContext = this;
        setContentView(R.layout.activity_native);
        initView();
        initNative();
    }

    private void initView() {
    }

    private void initNative() {
        mSitemajiNative = new SitemajiNative();
        mSitemajiNative.setNativeListener(new NativeListener() {
            @Override
            public void onClick() {
                Log.d(TAG, "onClick");
            }

            @Override
            public void onLoaded() {
                Log.d(TAG, "onLoaded");
            }

            @Override
            public void onLoadFail() {
                Log.d(TAG, "onLoadFail");
            }

            @Override
            public void onFail(int errorNo, String errorMessage) {
                Log.d(TAG, "onFail");
            }
        });
        mSitemajiNative.fetch(this, new SitemajiAdFetchListener() {
            @Override
            public void onSuccess() {
                ViewGroup rootView = findViewById(R.id.frameLayout);
                FrameLayout.LayoutParams layoutParams = new FrameLayout.LayoutParams(
                    FrameLayout.LayoutParams.MATCH_PARENT,
                    FrameLayout.LayoutParams.WRAP_CONTENT
                );
                mSitemajiNative.display(
                    NativeActivity.this,
                    rootView,
                    layoutParams
                );
            }

            @Override
            public void onFail(int errorNo, String errorMessage) {
                Log.d(TAG, String.format("Native onFail errorNo: %s errorMessage: %s", errorNo, errorMessage));
            }
        });
    }

    @Override
    protected void onResume() {
        super.onResume();
    }

    @Override
    protected void onDestroy() {
        super.onDestroy();
        if (mSitemajiNative != null) {
            mSitemajiNative.onDestroy();
        }
    }
}
  • NativeListener
public interface NativeListener {
    public void onClick();
    public void onLoaded();
    public void onLoadFail();
    public void onFail(int errorNo, String errorMessage);
}

Webview

You can assign layout_width szie, but it fixed ratio so suggest layout_height keep wrap_content.

  • View XML

     <com.sitemaji.view.SitemajiAdView
     	android:id="@+id/sitemajiAdView"
     	android:layout_width="150dp"
     	android:layout_height="wrap_content"
     	android:layout_centerInParent="true"/>
  • Java Code

     
     ...
     
     String AD_URL = "xxxx";    //  put ad url
     
     SitemajiAdView sitemajiAdView = (SitemajiAdView) findViewById(R.id.sitemajiAdView);
     mSitemajiAdView.setSitemajiAdViewStatusListener(new SitemajiAdViewStatusListener() {
         @Override
         public void onSuccess() {
             Log.i(TAG, "onSuccess");
         }
     
         @Override
         public void onFail() {
             Log.i(TAG, "onFail");
         }
     
         @Override
         public void onClick() {
             Log.i(TAG, "onClick");
         }
     });
     sitemajiAdView.loadUrl(AD_URL);
     
     ...
     
     @Override
     protected void onResume() {
         super.onResume();
         if (sitemajiAdView != null) {
             sitemajiAdView.onResume();
         }
     }
     
     
     @Override
     protected void onPause() {
     	super.onPause();
     	if (sitemajiAdView != null) {
     	    sitemajiAdView.onPause();
     	}
     }
     
     @Override
     protected void onDestroy() {
         super.onDestroy();
         if (sitemajiAdView != null) {
             sitemajiAdView.destroy();
         }
     }
     
     ...
     
  • SitemajiAdViewStatusListener

    public interface SitemajiAdViewStatusListener {
        void onSuccess();
        void onFail();
        void onClick();
    }
    
    
  • How to debug webview

     sitemajiAdView.setDebug(true);
    
  • Disable auto size

     sitemajiAdView.setAutoSize(false);
    

Cache

  • Config cache (1 hr), rule cache (30 min) you can manual clear Cache, can re-fetch provider config from remote server

     SitemajiCore.getInstance().resetCache();

Debug

  • You can enable SitemajiCore log or develop mode, the enable develop mode you can test all ad

     new SitemajiCore.Builder(this, PACKAGE_HASH)
         .withDevelopEnable(false)   // enable develop mode
         .withLogEnabled(true)   // enable log
         .build();
     
  • You can debug provider module status, use StiemjisXXX.setProviderStatusListener()

     mSitemajiVideo = new SitemajiVideo();
     mSitemajiVideo.setProviderStatusListener(new ProviderStatusListener() {
         @Override
         public void onProviderStatus(String provider, String status) {
             // provider status
         }
     });
     
  • ProviderStatusListener interface

     public interface ProviderStatusListener {
     
         public void onProviderStatus(String provider, String status);
     }
  • You you call deubg() print config info

     SitemajiCore.getInstance().debug()
     2019-02-23 15:31:05.860 10744-10744/com.sitemaji.open.demo D/SitemajiCore: Sitemaji key: e95f4dde6c22
     2019-02-23 15:31:05.860 10744-10744/com.sitemaji.open.demo D/SitemajiCore: Provider cache count: 5
     2019-02-23 15:31:05.860 10744-10744/com.sitemaji.open.demo D/SitemajiCore: [tapjoy] app id:  app key: xxxx
     2019-02-23 15:31:05.861 10744-10744/com.sitemaji.open.demo D/SitemajiCore: [clickforce] app id:  app key: 
     2019-02-23 15:31:05.861 10744-10744/com.sitemaji.open.demo D/SitemajiCore: [admod] app id:  app key: 
     2019-02-23 15:31:05.861 10744-10744/com.sitemaji.open.demo D/SitemajiCore: [inmobi] app id: xxxx app key: 
     2019-02-23 15:31:05.862 10744-10744/com.sitemaji.open.demo D/SitemajiCore: [flurry] app id:  app key: GKYJVB8MRDKYYZNC56ZX
     2019-02-23 15:31:05.863 10744-10744/com.sitemaji.open.demo D/SitemajiCore: [config] file last modify time: 51116-04-15 00:33:20
     2019-02-23 15:31:05.863 10744-10744/com.sitemaji.open.demo D/SitemajiCore: [config] file cache last modify timestamp: 1550906930000
     2019-02-23 15:31:05.863 10744-10744/com.sitemaji.open.demo D/SitemajiCore: ==================================
    

Q&A

  • How to support Android P Webview can't load HTTP Content

    1. put network_security_config.xml file to res/xml/ folder
    <?xml version="1.0" encoding="utf-8"?>
    <network-security-config>
        <base-config cleartextTrafficPermitted="true" />
    </network-security-config>    
    1. Add android:networkSecurityConfig
    <application
        ...
        android:networkSecurityConfig="@xml/network_security_config"
        ...
    />

Error No

  • Api Error
error no error message
1001 reponse body empty
1002 not support ad module
1003 app package error
1004 json format error
1005 api not support provider
  • Ad Error
error no error message
2001 not call fetch
2002 not call init
2003 already call init
2004 cache init error
2005 cache rule not found: %s
  • Network Error
error no error message
3001 network error
3999 network unknow error
  • Provider Error
error no error message
4001 provider %s init error
4002 cache not found provider: %s
4003 not call fetch ad
4004 not support android version
  • Server Error
error no error message
[http status code] server error
@WeiLianYang
Copy link
Copy Markdown

When I download a new package, the application will crash with the following message :
java.lang.RuntimeException: Unable to instantiate receiver com.mintegral.msdk.click.AppReceiver: java.lang.ClassNotFoundException: Didn't find class "com.mintegral.msdk.click.AppReceiver" on path: DexPathList[[zip file "/data/app/com.xxx.xxx-1/base.apk"],nativeLibraryDirectories=[/data/app/com.xxx.xxx-1/lib/arm64, /data/app/com.xxx.xxx-1/base.apk!/lib/arm64-v8a, /system/lib64, /vendor/lib64]]

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment