Java tutorial
/** * Copyright 2012 Scott Weeden-Moody * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ package com.lillicoder.newsblurry.util; import java.io.BufferedWriter; import java.io.File; import java.io.FileWriter; import java.io.IOException; import junit.framework.Assert; import org.json.JSONException; import org.json.JSONObject; import android.content.Context; import android.content.pm.ApplicationInfo; import android.content.pm.PackageManager; import android.content.pm.PackageManager.NameNotFoundException; import android.os.Environment; import android.text.TextUtils; import android.util.Log; /** * Utility class that can dump strings and {@link JSONObject} * values to a file in the app storage directory. * @author lillicoder */ public class FileLogger { private static final String TAG = FileLogger.class.getSimpleName(); private static final String DEBUG_WRITING_JSON_TO_FILE = "Writing JSON to file %s: %s"; private static final String DEBUG_WRITING_TEXT_TO_FILE = "Writing text to file %s: %s"; private static final String EXCEPTION_FAILED_TO_WRITE_OR_CLOSE_STREAM = "Failed to write to or close output stream, text was not logged."; private static final String WARNING_FAILED_TO_GET_APPLICATION_INFO = "Failed to get application info for package name %s, return false for debug mode."; private static final String WARNING_FAILED_TO_WRITE_DEBUG = "Failed to write data to debug stream, log operation will not be logged."; private Context _context; /** * Instantiates this object with the given {@link Context}. * @param context {@link Context} to get file directory access with. */ public FileLogger(Context context) { this._context = context; } /** * Gets this instance's {@link Context}. * @return {@link Context} for this instance. */ private Context getContext() { return this._context; } /** * Gets a {@link File} object for the given filename. If the indicated * file already exists, it will be overwritten by a new file. The returned file * lives in this app's external cache directory by default (when external * media is not available, the internal cache is used instead). * @param filename Filename of the file to get. * @return {@link File} object for the given filename. */ private File getLogFile(String filename) { Assert.assertTrue(!TextUtils.isEmpty(filename)); // Use cache directory so that files are removed on uninstall. Context context = this.getContext(); // Check for external media availability. If available, // write to that directory. Otherwise get the internal cache // directory and write there. File rootDirectory; if (this.isExternalStorageAvailable()) rootDirectory = context.getExternalCacheDir(); else rootDirectory = context.getCacheDir(); // If the file to write already exists, delete it. File logFile = new File(rootDirectory, filename); if (logFile.exists()) logFile.delete(); return logFile; } /** * Determines if this app is running in debug mode. This value is * automatically set via the build process. * @return <code>true</code> if the app is running in debug mode, * <code>false</code> otherwise. */ private boolean isDebugMode() { boolean isDebugMode = false; Context context = this.getContext(); PackageManager packageManager = context.getPackageManager(); try { ApplicationInfo appInfo = packageManager.getApplicationInfo(context.getPackageName(), 0); isDebugMode = (0 != (appInfo.flags &= ApplicationInfo.FLAG_DEBUGGABLE)); } catch (NameNotFoundException e) { Log.e(TAG, String.format(WARNING_FAILED_TO_GET_APPLICATION_INFO, context.getPackageName())); } return isDebugMode; } /** * Determines if the external storage media is available for writing. * @return <code>true</code> if external storage is available for writing, * <code>false</code> otherwise. */ private boolean isExternalStorageAvailable() { String externalMediaState = Environment.getExternalStorageState(); return Environment.MEDIA_MOUNTED.equals(externalMediaState); } /** * Dumps the given {@link JSONObject} to a file with the given * filename in the app storage directory. * @param filename Filename of the file to dump to. If the specified file already * exists, its contents will be overwritten. * @param jsonToDump {@link JSONObject} to write to a file. * @return <code>true</code> if the log was successfully written, * <code>false</code> otherwise. */ public boolean logJson(String filename, JSONObject jsonToDump) { Assert.assertTrue(!TextUtils.isEmpty(filename) && jsonToDump != null); try { if (this.isDebugMode()) Log.d(TAG, String.format(DEBUG_WRITING_JSON_TO_FILE, filename, jsonToDump.toString(4))); } catch (JSONException e) { Log.w(TAG, WARNING_FAILED_TO_WRITE_DEBUG); } File logFile = this.getLogFile(filename); return this.writeLog(logFile, jsonToDump.toString()); } /** * Dumps the given {@link CharSequence} to a file with the given * filename in the app storage directory. * @param filename Filename of the file to dump to. If the specified file already * exists, its contents will be overwritten. * @param textToDump {@link CharSequence} to write to file. * @return <code>true</code> if the log was successfully written, * <code>false</code> otherwise. */ public boolean logText(String filename, CharSequence textToDump) { Assert.assertTrue(!TextUtils.isEmpty(filename) && !TextUtils.isEmpty(textToDump)); if (this.isDebugMode()) Log.d(TAG, String.format(DEBUG_WRITING_TEXT_TO_FILE, filename, textToDump)); File logFile = this.getLogFile(filename); return this.writeLog(logFile, textToDump.toString()); } /** * Writes the given string to the given log {@link File}. * @param logFile {@link File} to write to. * @param textToLog String to write to file. * @return <code>true</code> if file was successfully written, * <code>false</code> if there was an error writing to the file. */ private boolean writeLog(File logFile, String textToLog) { Assert.assertTrue(logFile != null && !TextUtils.isEmpty(textToLog)); boolean hasWrittenLog = false; try { // Write the string to the log and close. BufferedWriter buffer = new BufferedWriter(new FileWriter(logFile, false)); buffer.write(textToLog); buffer.close(); hasWrittenLog = true; } catch (IOException e) { Log.e(TAG, EXCEPTION_FAILED_TO_WRITE_OR_CLOSE_STREAM); } return hasWrittenLog; } }