Add statics:

This commit is contained in:
hyb1996 2017-05-05 16:54:25 +08:00
parent 163f38760e
commit 68845c9a21
13 changed files with 488 additions and 134 deletions

View File

@ -3,13 +3,13 @@ def AAVersion = '4.2.0'
android {
compileSdkVersion 25
buildToolsVersion "25.0.1"
buildToolsVersion "25.0.2"
defaultConfig {
applicationId "com.stardust.scriptdroid"
minSdkVersion 19
targetSdkVersion 23
versionCode 119
versionName "2.0.8 Beta"
versionCode 120
versionName "2.0.9 Beta"
testInstrumentationRunner "android.support.test.runner.AndroidJUnitRunner"
multiDexEnabled true
}
@ -49,6 +49,9 @@ android {
pickFirst 'org/mozilla/javascript/*.java.orig'
pickFirst 'org/mozilla/javascript/tools/resources/*.properties'
}
configurations.all {
resolutionStrategy.force 'com.google.code.findbugs:jsr305:3.0.1'
}
}
repositories {
@ -58,13 +61,16 @@ repositories {
}
dependencies {
androidTestCompile('com.android.support.test.espresso:espresso-core:2.2.2', {
exclude group: 'com.android.support', module: 'support-annotations'
})
testCompile 'junit:junit:4.12'
debugCompile 'com.squareup.leakcanary:leakcanary-android:1.5'
releaseCompile 'com.squareup.leakcanary:leakcanary-android-no-op:1.5'
testCompile 'com.squareup.leakcanary:leakcanary-android-no-op:1.5'
annotationProcessor "org.androidannotations:androidannotations:$AAVersion"
compile "org.androidannotations:androidannotations-api:$AAVersion"
compile 'com.android.support:appcompat-v7:25.1.0'
annotationProcessor 'com.pushtorefresh.storio:sqlite-annotations-processor:1.12.3'
compile 'com.pushtorefresh.storio:sqlite-annotations:1.12.3'
compile 'com.android.support:appcompat-v7:25.3.0'
compile 'com.android.support:design:25.1.0'
compile 'com.github.hyb1996:MutableTheme:0.2.2'
compile 'com.afollestad.material-dialogs:core:0.9.2.3'
@ -85,6 +91,7 @@ dependencies {
compile 'com.android.volley:volley:1.0.0'
compile 'com.github.hyb1996:EnhancedFloaty:0.15'
compile 'com.flurry.android:analytics:7.0.0@aar'
compile 'com.pushtorefresh.storio:sqlite:1.12.3'
compile 'com.android.support:multidex:1.0.1'
compile(name: 'libtermexec-release', ext: 'aar')
compile(name: 'emulatorview-release', ext: 'aar')

View File

@ -0,0 +1,97 @@
package com.stardust.scriptdroid.statics;
import android.support.test.InstrumentationRegistry;
import com.stardust.autojs.script.FileScriptSource;
import com.stardust.autojs.script.ScriptSource;
import com.stardust.autojs.script.StringScriptSource;
import com.stardust.util.MapEntries;
import org.junit.Before;
import org.junit.Test;
import static org.junit.Assert.*;
/**
* Created by Stardust on 2017/5/5.
*/
public class SQLiteStaticsStorageTest {
private SQLiteStaticsStorage mStorage;
@Before
public void setUp() throws Exception {
mStorage = new SQLiteStaticsStorage(InstrumentationRegistry.getTargetContext());
}
@Test
public void record() throws Exception {
testOneRecord();
testTwoRecord();
testRepeatedRecord();
}
@Test
public void testOneRecord() {
mStorage.clear();
mStorage.record(new StringScriptSource("Name", "Script"));
assertEquals(mStorage.getAll(), new MapEntries<String, String>()
.entry("Name.js", "1")
.map());
}
@Test
public void testTwoRecord() {
mStorage.clear();
mStorage.record(new StringScriptSource("Name", "Script"));
mStorage.record(new FileScriptSource("/test/test.js"));
assertEquals(mStorage.getAll(), new MapEntries<String, String>()
.entry("Name.js", "1")
.entry("/test/test.js", "1")
.map());
}
@Test
public void testRepeatedRecord() {
mStorage.clear();
mStorage.record(new FileScriptSource("/test/test.js"));
mStorage.record(new StringScriptSource("Name", "Script"));
mStorage.record(new FileScriptSource("/test/test.js"));
mStorage.record(new FileScriptSource("/test/test.js"));
assertEquals(mStorage.getAll(), new MapEntries<String, String>()
.entry("Name.js", "1")
.entry("/test/test.js", "3")
.map());
}
@Test
public void getMax() throws Exception {
mStorage.clear();
put(new FileScriptSource("/test/test.js"), 50);
put(new StringScriptSource("Name4", "Script"), 10);
put(new StringScriptSource("Name5", "Script"), 5);
put(new StringScriptSource("Name6", "Script"), 4);
put(new StringScriptSource("Name7", "Script"), 3);
put(new StringScriptSource("Name8", "Script"), 1);
put(new StringScriptSource("Name9", "Script"), 1);
put(new StringScriptSource("Name3", "Script"), 20);
put(new StringScriptSource("Name1", "Script"), 100);
assertEquals(mStorage.getMax(5), new MapEntries<String, String>()
.entry("Name1.js", "100")
.entry("/test/test.js", "50")
.entry("Name3.js", "20")
.entry("Name4.js", "10")
.entry("Name5.js", "5")
.map());
}
private void put(ScriptSource source, int times) {
for (int i = 0; i < times; i++) {
mStorage.record(source);
}
}
}

View File

@ -13,6 +13,7 @@ import com.stardust.app.SimpleActivityLifecycleCallbacks;
import com.stardust.app.VolumeChangeObserver;
import com.stardust.scriptdroid.autojs.AutoJs;
import com.stardust.scriptdroid.service.AccessibilityWatchDogService;
import com.stardust.scriptdroid.statics.ScriptStatics;
import com.stardust.scriptdroid.tool.CrashHandler;
import com.stardust.scriptdroid.tool.JsBeautifierFactory;
import com.stardust.scriptdroid.ui.error.ErrorReportActivity;
@ -49,9 +50,7 @@ public class App extends MultiDexApplication {
}
private void setUpStaticsTool() {
new FlurryAgent.Builder()
.withLogEnabled(true)
.build(this, "D42MH48ZN4PJC5TKNYZD");
ScriptStatics.init(this);
}
@ -91,7 +90,6 @@ public class App extends MultiDexApplication {
@Override
public void onActivityCreated(Activity activity, Bundle savedInstanceState) {
super.onActivityCreated(activity, savedInstanceState);
FlurryAgent.logEvent(activity.getClass().getSimpleName());
}
@Override

View File

@ -5,6 +5,7 @@ import com.stardust.autojs.execution.ScriptExecution;
import com.stardust.autojs.execution.ScriptExecutionListener;
import com.stardust.scriptdroid.App;
import com.stardust.scriptdroid.R;
import com.stardust.scriptdroid.statics.ScriptStatics;
/**
* Created by Stardust on 2017/5/3.
@ -16,7 +17,7 @@ public class ScriptExecutionGlobalListener implements ScriptExecutionListener {
@Override
public void onStart(ScriptExecution execution) {
execution.getEngine().setTag(ENGINE_TAG_START_TIME, System.currentTimeMillis());
FlurryAgent.logEvent("EXEC:" + execution.getSource().toString());
ScriptStatics.recordScript(execution.getSource());
}
@Override

View File

@ -7,10 +7,16 @@ import android.util.Log;
import com.stardust.autojs.runtime.ScriptInterruptedException;
import com.stardust.autojs.runtime.api.AbstractShell;
import com.stardust.lang.ThreadCompat;
import com.stardust.pio.UncheckedIOException;
import com.stardust.scriptdroid.App;
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.io.OutputStream;
import java.io.PipedInputStream;
import java.io.PipedOutputStream;
import jackpal.androidterm.ShellTermSession;
import jackpal.androidterm.emulatorview.TermSession;
@ -22,19 +28,23 @@ import jackpal.androidterm.util.TermSettings;
public class Shell extends AbstractShell implements AutoCloseable {
public interface OutputListener {
void onNewOutput(String str);
public interface Callback {
void onNewLine(String str);
void onInitialized();
void onInterrupted(InterruptedException e);
}
private static final String TAG = "Shell";
private TermSession mTermSession;
private RuntimeException mInitException;
private final Object mInitLock = new Object();
private final Object mExitLock = new Object();
private boolean mInitialized = false;
private boolean mWaitingExit = false;
private OutputListener mOutputListener;
private volatile RuntimeException mInitException;
private volatile boolean mInitialized = false;
private volatile boolean mWaitingExit = false;
private Callback mCallback;
public Shell() {
super();
@ -69,8 +79,12 @@ public class Shell extends AbstractShell implements AutoCloseable {
mTermSession.write(command + "\n");
}
public void setOutputListener(OutputListener outputListener) {
mOutputListener = outputListener;
public void setCallback(Callback callback) {
mCallback = callback;
}
public boolean isInitialized() {
return mInitialized;
}
private void ensureInitialized() {
@ -97,12 +111,20 @@ public class Shell extends AbstractShell implements AutoCloseable {
try {
mInitLock.wait();
} catch (InterruptedException e) {
exit();
throw new ScriptInterruptedException();
onInterrupted(e);
}
}
}
private void onInterrupted(InterruptedException e) {
if (mCallback == null) {
exit();
throw new ScriptInterruptedException();
} else {
mCallback.onInterrupted(e);
}
}
@Override
public void exit() {
mTermSession.finish();
@ -124,8 +146,7 @@ public class Shell extends AbstractShell implements AutoCloseable {
try {
mExitLock.wait();
} catch (InterruptedException e) {
exit();
throw new ScriptInterruptedException();
onInterrupted(e);
}
}
}
@ -137,31 +158,65 @@ public class Shell extends AbstractShell implements AutoCloseable {
private class MyShellTermSession extends ShellTermSession {
private BufferedReader mBufferedReader;
private OutputStream mOutputStream;
private Thread mReadingThread;
public MyShellTermSession(TermSettings settings, String initialCommand) throws IOException {
super(settings, initialCommand);
PipedInputStream pipedInputStream = new PipedInputStream(8192);
mBufferedReader = new BufferedReader(new InputStreamReader(pipedInputStream));
mOutputStream = new PipedOutputStream(pipedInputStream);
startReadingThread();
}
@Override
protected void processInput(byte[] data, int offset, int count) {
String output = new String(data, offset, count);
Log.d(TAG, output);
if(mOutputListener != null){
mOutputListener.onNewOutput(output);
}
if (mInitialized && !mWaitingExit) {
return;
}
String[] lines = new String(data, offset, count).split("\n");
for (String line : lines) {
if (!mInitialized && line.endsWith(" # ")) {
private void startReadingThread() {
mReadingThread = new ThreadCompat(new Runnable() {
@Override
public void run() {
String line;
try {
while (!Thread.currentThread().isInterrupted()
&& (line = mBufferedReader.readLine()) != null) {
onNewLine(line);
}
} catch (IOException e) {
e.printStackTrace();
}
}
});
mReadingThread.start();
}
private void onNewLine(String line) {
Log.d(TAG, line);
if (mInitialized) {
if (mCallback != null) {
mCallback.onNewLine(line);
}
} else {
if (isRoot() && line.endsWith(" $ su")) {
notifyInitialized();
return;
}
if (mWaitingExit && line.endsWith(" $ ")) {
notifyExit();
if (!isRoot() && line.endsWith(" $ ")) {
notifyInitialized();
return;
}
}
if (mWaitingExit && line.endsWith(" exit")) {
notifyExit();
}
}
@Override
protected void processInput(byte[] data, int offset, int count) {
try {
mOutputStream.write(data, offset, count);
} catch (IOException e) {
throw new UncheckedIOException(e);
}
}
private void notifyExit() {
@ -176,6 +231,9 @@ public class Shell extends AbstractShell implements AutoCloseable {
synchronized (mInitLock) {
mInitLock.notifyAll();
}
if (mCallback != null) {
mCallback.onInitialized();
}
}
@Override
@ -186,6 +244,18 @@ public class Shell extends AbstractShell implements AutoCloseable {
mExitLock.notify();
}
}
@Override
public void finish() {
super.finish();
mReadingThread.interrupt();
try {
mBufferedReader.close();
mOutputStream.close();
} catch (IOException e) {
e.printStackTrace();
}
}
}
}

View File

@ -66,7 +66,7 @@ public class RecordNavigatorContent implements NavigatorContent, Recorder.OnStat
if (Pref.isRecordVolumeControlEnable()) {
if (mRecorder == null) {
startRecord();
} else if (mRecorder.getState() == Recorder.STATE_RECORDING) {
} else if (alreadyStartedRecord()) {
stopRecord();
}
}
@ -211,7 +211,7 @@ public class RecordNavigatorContent implements NavigatorContent, Recorder.OnStat
@Override
public void onKeyDown(String keyName) {
if (keyName.equals(Pref.getStopRecordTrigger())) {
if (mRecorder != null && mRecorder.getState() == Recorder.STATE_RECORDING && mRecorder.getState() == Recorder.STATE_PAUSED)
if (alreadyStartedRecord())
stopRecord();
} else if (keyName.equals(Pref.getStartRecordTrigger())) {
if (mRecorder == null)
@ -219,6 +219,10 @@ public class RecordNavigatorContent implements NavigatorContent, Recorder.OnStat
}
}
private boolean alreadyStartedRecord() {
return mRecorder != null && mRecorder.getState() == Recorder.STATE_RECORDING && mRecorder.getState() == Recorder.STATE_PAUSED;
}
@Override
public void onKeyUp(String keyName) {

View File

@ -9,6 +9,7 @@ import com.stardust.scriptdroid.App;
import com.stardust.scriptdroid.R;
import com.stardust.scriptdroid.autojs.AutoJs;
import com.stardust.scriptdroid.record.Recorder;
import com.stardust.util.MapEntries;
import org.greenrobot.eventbus.EventBus;
@ -72,9 +73,9 @@ public abstract class InputEventConverter {
private int mState = Recorder.STATE_NOT_START;
public void convertEventIfFormatCorrect(String eventStr) {
if(!mConverting)
if (!mConverting)
return;
if(TextUtils.isEmpty(eventStr) || !eventStr.startsWith("["))
if (TextUtils.isEmpty(eventStr) || !eventStr.startsWith("["))
return;
Event event = parseEventOrNull(eventStr);
if (event != null) {
@ -94,7 +95,7 @@ public abstract class InputEventConverter {
mState = Recorder.STATE_RECORDING;
}
public void resume(){
public void resume() {
mConverting = true;
mState = Recorder.STATE_RECORDING;
}
@ -118,10 +119,12 @@ public abstract class InputEventConverter {
return Event.parseEvent(eventStr);
} catch (EventFormatException e) {
e.printStackTrace();
if(mFirstEventFormatError){
if (mFirstEventFormatError) {
Toast.makeText(App.getApp(), R.string.text_record_format_error, Toast.LENGTH_SHORT).show();
mFirstEventFormatError = false;
FlurryAgent.logEvent("EventFormatException:" + e.getMessage());
FlurryAgent.logEvent("EventFormatException", new MapEntries<String, String>()
.entry("message", e.getMessage())
.map());
}
return null;
}

View File

@ -5,6 +5,7 @@ import android.util.Log;
import com.stardust.pio.UncheckedIOException;
import com.stardust.scriptdroid.App;
import com.stardust.scriptdroid.autojs.Shell;
import com.stardust.scriptdroid.record.Recorder;
import java.io.BufferedReader;
@ -22,27 +23,39 @@ import jackpal.androidterm.util.TermSettings;
* Created by Stardust on 2017/3/6.
*/
public class InputEventRecorder extends Recorder.AbstractRecorder {
public class InputEventRecorder extends Recorder.AbstractRecorder {
private static final String TAG = "InputEventRecorder";
private TermSession mTermSession;
private String mGetEventCommand;
private Shell mShell;
protected InputEventConverter mInputEventConverter;
protected InputEventRecorder(InputEventConverter inputEventConverter) {
mGetEventCommand = inputEventConverter.getGetEventCommand();
mInputEventConverter = inputEventConverter;
}
public void listen() {
TermSettings settings = new TermSettings(App.getApp().getResources(), PreferenceManager.getDefaultSharedPreferences(App.getApp()));
try {
mTermSession = new MyShellTermSession(settings, "su");
mTermSession.initializeEmulator(80, 40);
} catch (IOException e) {
throw new RuntimeException(e);
}
mShell = new Shell(true);
mShell.setCallback(new Shell.Callback() {
@Override
public void onNewLine(String str) {
if (mShell.isInitialized()) {
convertEvent(str);
}
}
@Override
public void onInitialized() {
mShell.exec(mGetEventCommand);
}
@Override
public void onInterrupted(InterruptedException e) {
stop();
}
});
}
@Override
@ -62,7 +75,7 @@ public class InputEventRecorder extends Recorder.AbstractRecorder {
@Override
protected void stopImpl() {
mTermSession.finish();
mShell.exit();
mInputEventConverter.stop();
}
@ -75,70 +88,4 @@ public class InputEventRecorder extends Recorder.AbstractRecorder {
mInputEventConverter.convertEventIfFormatCorrect(eventStr);
}
private class MyShellTermSession extends ShellTermSession {
private volatile boolean mGettingEvents = false;
private BufferedReader mBufferedReader;
private OutputStream mOutputStream;
private Thread mReadingThread;
public MyShellTermSession(TermSettings settings, String initialCommand) throws IOException {
super(settings, initialCommand);
PipedInputStream pipedInputStream = new PipedInputStream(8192);
mBufferedReader = new BufferedReader(new InputStreamReader(pipedInputStream));
mOutputStream = new PipedOutputStream(pipedInputStream);
startReadingThread();
}
private void startReadingThread() {
mReadingThread = new Thread(new Runnable() {
@Override
public void run() {
String line;
try {
while (!Thread.currentThread().isInterrupted()
&& (line = mBufferedReader.readLine()) != null){
onNewLine(line);
}
} catch (IOException e) {
e.printStackTrace();
}
}
});
mReadingThread.start();
}
private void onNewLine(String line) {
Log.d(TAG, line);
if (!mGettingEvents && line.endsWith(" $ su")) {
mTermSession.write(mGetEventCommand + "\r");
mGettingEvents = true;
} else if (mGettingEvents) {
convertEvent(line);
}
}
@Override
protected void processInput(byte[] data, int offset, int count) {
try {
mOutputStream.write(data, offset, count);
} catch (IOException e) {
throw new UncheckedIOException(e);
}
}
@Override
public void finish() {
super.finish();
mReadingThread.interrupt();
try {
mBufferedReader.close();
mOutputStream.close();
} catch (IOException e) {
e.printStackTrace();
}
}
}
}

View File

@ -1,12 +1,10 @@
package com.stardust.scriptdroid.record.inputevent;
import com.stardust.scriptdroid.Pref;
/**
* Created by Stardust on 2017/3/16.
*/
public class TouchRecorder extends InputEventRecorder implements KeyObserver.KeyListener {
public class TouchRecorder extends InputEventRecorder {
public TouchRecorder() {
super(new InputEventToSendEventJsConverter());
@ -19,14 +17,4 @@ public class TouchRecorder extends InputEventRecorder implements KeyObserver.Key
super.stop();
}
@Override
public void onKeyDown(String keyName) {
}
@Override
public void onKeyUp(String keyName) {
}
}

View File

@ -0,0 +1,140 @@
package com.stardust.scriptdroid.statics;
import android.content.Context;
import android.database.sqlite.SQLiteDatabase;
import com.pushtorefresh.storio.sqlite.SQLiteTypeMapping;
import com.pushtorefresh.storio.sqlite.StorIOSQLite;
import com.pushtorefresh.storio.sqlite.impl.DefaultStorIOSQLite;
import com.pushtorefresh.storio.sqlite.queries.DeleteQuery;
import com.pushtorefresh.storio.sqlite.queries.Query;
import com.stardust.autojs.script.ScriptSource;
import java.io.IOException;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
/**
* Created by Stardust on 2017/5/5.
*/
public class SQLiteStaticsStorage implements ScriptStaticsStorage {
private static final int VERSION = 1;
private static final String DATABASE_NAME = "Ever.db";
static final String TABLE_NAME = "FinalEating";
private StorIOSQLite mStorIOSQLite;
public SQLiteStaticsStorage(Context context) {
mStorIOSQLite = DefaultStorIOSQLite.builder()
.sqliteOpenHelper(new SQLiteOpenHelper(context))
.addTypeMapping(ScriptStaticsRecord.class, new ScriptStaticsRecordSQLiteTypeMapping())
.build();
}
@Override
public void record(ScriptSource source) {
int times = getTimes(source) + 1;
mStorIOSQLite.put()
.object(new ScriptStaticsRecord(source.toString(), times))
.prepare()
.executeAsBlocking();
}
public int getTimes(ScriptSource source) {
ScriptStaticsRecord record = mStorIOSQLite.get()
.object(ScriptStaticsRecord.class)
.withQuery(Query.builder()
.table(TABLE_NAME)
.where("name = ?")
.whereArgs(source.toString())
.build())
.prepare()
.executeAsBlocking();
if (record != null) {
return record.times;
} else {
return 0;
}
}
@Override
public Map<String, String> getAll() {
List<ScriptStaticsRecord> records = mStorIOSQLite.get()
.listOfObjects(ScriptStaticsRecord.class)
.withQuery(Query.builder()
.table(TABLE_NAME)
.orderBy("times")
.build())
.prepare()
.executeAsBlocking();
return toMap(records);
}
private Map<String, String> toMap(List<ScriptStaticsRecord> records) {
Map<String, String> map = new HashMap<>();
for (ScriptStaticsRecord record : records) {
map.put(record.name, String.valueOf(record.times));
}
return map;
}
@Override
public Map<String, String> getMax(int size) {
List<ScriptStaticsRecord> records = mStorIOSQLite.get()
.listOfObjects(ScriptStaticsRecord.class)
.withQuery(Query.builder()
.table(TABLE_NAME)
.orderBy("times DESC")
.limit(size)
.build())
.prepare()
.executeAsBlocking();
return toMap(records);
}
@Override
public void clear() {
mStorIOSQLite.delete()
.byQuery(DeleteQuery.builder()
.table(TABLE_NAME)
.build())
.prepare()
.executeAsBlocking();
}
@Override
public void close() {
try {
mStorIOSQLite.close();
} catch (IOException e) {
e.printStackTrace();
}
}
private static class SQLiteOpenHelper extends android.database.sqlite.SQLiteOpenHelper {
SQLiteOpenHelper(Context context) {
super(context, DATABASE_NAME, null, VERSION);
}
@Override
public void onCreate(SQLiteDatabase db) {
db.execSQL("CREATE TABLE IF NOT EXISTS " + TABLE_NAME + "(\n"
+ "name TEXT NOT NULL PRIMARY KEY, "
+ "times INTEGER"
+ ");");
}
@Override
public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) {
}
}
}

View File

@ -0,0 +1,49 @@
package com.stardust.scriptdroid.statics;
import android.content.Context;
import android.content.SharedPreferences;
import android.preference.PreferenceManager;
import android.text.format.DateUtils;
import com.flurry.android.FlurryAgent;
import com.stardust.autojs.script.ScriptSource;
import com.stardust.scriptdroid.BuildConfig;
/**
* Created by Stardust on 2017/5/5.
*/
public class ScriptStatics {
private static final String KEY_MILLIS = "Sorry, I should have left";
private static ScriptStaticsStorage storage;
private static SharedPreferences preferences;
public static void init(Context context) {
storage = new SQLiteStaticsStorage(context);
new FlurryAgent.Builder()
.withLogEnabled(BuildConfig.DEBUG)
.build(context, "D42MH48ZN4PJC5TKNYZD");
preferences = PreferenceManager.getDefaultSharedPreferences(context);
}
public static void recordScript(ScriptSource source) {
storage.record(source);
sendStaticsIfNeeded();
}
private static void sendStaticsIfNeeded() {
long millis = preferences.getLong(KEY_MILLIS, 0);
if (!DateUtils.isToday(millis)) {
preferences.edit().putLong(KEY_MILLIS, System.currentTimeMillis()).apply();
FlurryAgent.logEvent("ScriptStatics", storage.getMax(10));
}
}
@Override
protected void finalize() throws Throwable {
super.finalize();
storage.close();
}
}

View File

@ -0,0 +1,28 @@
package com.stardust.scriptdroid.statics;
import com.pushtorefresh.storio.sqlite.annotations.StorIOSQLiteColumn;
import com.pushtorefresh.storio.sqlite.annotations.StorIOSQLiteCreator;
import com.pushtorefresh.storio.sqlite.annotations.StorIOSQLiteType;
/**
* Created by Stardust on 2017/5/5.
*/
@StorIOSQLiteType(table = SQLiteStaticsStorage.TABLE_NAME)
public class ScriptStaticsRecord {
@StorIOSQLiteColumn(name = "name", key = true)
public String name;
@StorIOSQLiteColumn(name = "times")
public int times;
public ScriptStaticsRecord(String name, int times) {
this.name = name;
this.times = times;
}
public ScriptStaticsRecord() {
}
}

View File

@ -0,0 +1,22 @@
package com.stardust.scriptdroid.statics;
import com.stardust.autojs.script.ScriptSource;
import java.util.Map;
/**
* Created by Stardust on 2017/5/5.
*/
public interface ScriptStaticsStorage {
void record(ScriptSource source);
Map<String, String> getAll();
Map<String, String> getMax(int size);
void clear();
void close();
}