FileReader producing a NPE - java

I have a file stored locally on my device that I read from perfectly fine if I don't reboot the phone. When I reboot and read the logs, new FileReader throws an NPE; why?
BufferedReader br = null;
FileReader fr = null;
try {
Log.d("DEBUG", "Before filereader");
fr = new FileReader(ABS_FILENAME);
Log.d("DEBUG", "Before BufferedReader");
br = new BufferedReader(fr);
String current;
Log.d("DEBUG", "About to read file");
while((current = br.readLine()) != null) {
}
}
} catch (Exception e) {
Log.d("DEBUG", "Exception thrown: " + e.getMessage());
} finally {
try {
if (fr != null) {
fr.close();
}
} catch (IOException ex) {
Log.d("DEBUG", "Problem closing file reader");
}
}
return null;
The above code happens in a broadcast receiver. ABS_FILENAME is a string that denotes a file. That file is written to periodically in an Activity once something is clicked:
// in an onClick that gets invoked
try {
String line = myKey + " " + myValue;
fw.write(line);
fw.write(System.getProperty("line.separator"));
} catch (IOException e) {
e.printStackTrace();
} finally {
try {
if(fw != null)
fw.close();
} catch (IOException e) {
e.printStackTrace();
}
}
// elsewhere in the activity
#Override protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_my);
myFile = new File(getFilesDir(), FILENAME);
try {
if (!myFile.exists()) {
myFile.createNewFile();
}
ABS_FILENAME = myFile.getAbsolutePath();
fw = new FileWriter(myFile.getAbsoluteFile(), true);
} catch(IOException e) {
}

If
new FileReader(ABS_FILENAME)
really produces a NullPointerException, clearly ABS_FILENAME must be null.

Related

Why I have Permission denied on a file located in /data/user_de/

I want to get the attached content of MMS like Image or Video/audio.
First I make this
static void getMmsContent(Context context, ArrayList<Mms> mmsArrayList) {
try {
for (Mms unMms : mmsArrayList) {
ContentResolver contentResolver = context.getContentResolver();
Uri uri = Uri.parse("content://mms/part");
String selection = Telephony.Mms.Part.MSG_ID + "=" + unMms.getId();
Cursor query = contentResolver.query(uri, null, selection, null, null);
if (query != null && query.moveToFirst()) {
do {
String name = query.getString(query.getColumnIndex("name"));
String type = query.getString(query.getColumnIndex("ct"));
String txt = query.getString(query.getColumnIndex(Telephony.Mms.Part.TEXT));
String data = query.getString(query.getColumnIndex(Telephony.Mms.Part._DATA));
if (!type.equals("application/smil")) {
String[] dataMms = {name, type, txt, data};
getContent(context, dataMms, unMms);
}
} while (query.moveToNext());
}
if (query != null) {
query.close();
}
}
} catch (Exception e) {
Log.d("Exception", e.toString());
}
}
This line give me the path to the location of the attached content.
String data = query.getString(query.getColumnIndex(Telephony.Mms.Part._DATA));
/data/user_de/0/com.android.providers.telephony/app_parts/PART_1555841710097_Screenshot_20190421-121445_Chrome1.jpg
So now i want to transform the image to a Bitmap to add it to a zip file.
static private void getContent(Context context, String[] dataMms, Mms unMms){
if (dataMms[1].equals("text/plain")) {
unMms.setCorps(dataMms[2]);
} else {
if ("image/jpeg".equals(dataMms[1]) || "image/bmp".equals(dataMms[1]) ||
"image/gif".equals(dataMms[1]) || "image/jpg".equals(dataMms[1]) ||
"image/png".equals(dataMms[1])) {
unMms.setTypeContenu(dataMms[1]);
Bitmap bitmap = null;
InputStream is = null;
try {
File source = new File(dataMms[3]);
is = new FileInputStream(source);
bitmap = BitmapFactory.decodeStream(is);
} catch (IOException e) {
Log.d("Exception", e.toString());
} finally {
if (is != null) {
try {
is.close();
} catch (IOException e) {
Log.d("Exception", e.toString());
}
}
}
if (bitmap != null) {
File file = new File(context.getApplicationInfo().dataDir + "/files/", dataMms[0]);
OutputStream Fout = null;
try {
Fout = new FileOutputStream(file);
bitmap.compress(Bitmap.CompressFormat.PNG, 100, Fout);
Fout.flush();
Fout.close();
} catch (FileNotFoundException e) {
Log.d("Exception", e.toString());
} catch (IOException e) {
Log.d("Exception", e.toString());
}
}
}
}
}
But my code Throw a Exception on new FileInputStream(source);
I got this
D/Exception: java.io.FileNotFoundException: /data/user_de/0/com.android.providers.telephony/app_parts/PART_1547316880687_Resized_20190112_191438_9422.jpeg (Permission denied)
I have the permissions and i have require the user permission.
<uses-permission android:name="android.permission.READ_SMS" />
<uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE" />
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE"/>
So i change my code after the comment of CommonsWare to this :
static private void getContent(Context context, String[] dataMms, Mms unMms) {
if (dataMms[1].equals("text/plain")) {
unMms.setCorps(dataMms[2]);
} else {
if ("image/jpeg".equals(dataMms[1]) || "image/bmp".equals(dataMms[1]) ||
"image/gif".equals(dataMms[1]) || "image/jpg".equals(dataMms[1]) ||
"image/png".equals(dataMms[1])) {
unMms.setTypeContenu(dataMms[1]);
Uri partURI = Uri.parse("content://mms/part/" + dataMms[4]);
InputStream is = null;
Bitmap bitmap = null;
try {
is = context.getContentResolver().openInputStream(partURI);
bitmap = BitmapFactory.decodeStream(is);
} catch (IOException e) {
Log.d("Exception", e.toString());
} finally {
if (is != null) {
try {
is.close();
} catch (IOException e) {
Log.d("Exception", e.toString());
}
}
}
if (bitmap != null) {
File file = new File(context.getApplicationInfo().dataDir + "/files/", dataMms[0]);
OutputStream Fout = null;
try {
file.createNewFile();
Fout = new FileOutputStream(file);
bitmap.compress(Bitmap.CompressFormat.PNG, 100, Fout);
Fout.flush();
Fout.close();
} catch (FileNotFoundException e) {
Log.d("Exception", e.toString());
} catch (IOException e) {
Log.d("Exception", e.toString());
}
}
}
}
}
The tricky part is this :
Uri partURI = Uri.parse("content://mms/part/" + dataMms[4]);
my dataMms[4] is the id of the MMS Part, I get it from this line I put on getMmsContent() :
String id = query.getString(query.getColumnIndex("_id"));
This column give me the id of the part.
But there is no mention about this column in Android Developer documentation : https://developer.android.com/reference/android/provider/Telephony.Mms.Part.html
So I listed the columns with this code in getMmsContent() and I found it :
for (int i = 0; i < query.getColumnCount(); i++) {
Log.i("Column", query.getColumnName(i));
}
Now It's working !

Reading music from asset folder

My project is list of music that user can set as ringtone.
All of my music is located in raw and it works correctly and also my ringtone name is a text in raw "zeallist".
My problem is that how to put my music in asset folder.
Here is my code that play music from raw:
public ArrayList<SongInfo> getAllSong(Context context) {
ArrayList<SongInfo> listSong = new ArrayList<SongInfo>();
RingtonesSharedPreferences pref = new RingtonesSharedPreferences(
context);
Field[] fields = R.raw.class.getFields();
for (int i = 0; i < fields.length - 1; i++) {
SongInfo info = new SongInfo();
try {
String name = fields[i].getName();
if (!name.equals("ringtones")) {
info.setFileName(name + ".mp3");
info.setFavorite(pref.getString(info.getFileName()));
int audioResource = R.raw.class.getField(name).getInt(name);
info.setAudioResource(audioResource);
}
// info.setName(name);
} catch (Exception e) {
}
listSong.add(info);
}
InputStream inputStream = context.getResources().openRawResource(
R.raw.zeallist);
BufferedReader reader = new BufferedReader(new InputStreamReader(
inputStream));
try {
String line;
int i = 0;
while ((line = reader.readLine()) != null) {
listSong.get(i).setName(line);
i++;
}
} catch (Exception e) {
// TODO: handle exception
} finally {
try {
reader.close();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
return listSong;
}
How to change this part of my code to read them from asset and return my listsong ?
Core part I have finished.Some details you need do yourself
public ArrayList<SongInfo> getAllSong(Context context) throws IOException {
ArrayList<SongInfo> listSong = new ArrayList<SongInfo>();
RingtonesSharedPreferences pref = new RingtonesSharedPreferences(context);
String[] files = context.getAssets().list("Your songs path");
for (int i = 0; i < files.length - 1; i++) {
SongInfo info = new SongInfo();
String name = files[i];
if (!name.equals("ringtones")) {
info.setFileName(name + ".mp3");
info.setFavorite(pref.getString(info.getFileName()));
/* int audioResource = R.raw.class.getField(name).getInt(name);
info.setAudioResource(audioResource);*/ //fileName is enough to you
}
// info.setName(name);
listSong.add(info);
}
InputStream inputStream = context.getAssets().open("Your zeallist path");
BufferedReader reader = new BufferedReader(new InputStreamReader(
inputStream));
try {
String line;
int i = 0;
while ((line = reader.readLine()) != null) {
listSong.get(i).setName(line);
i++;
}
} catch (Exception e) {
// TODO: handle exception
} finally {
try {
reader.close();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
return listSong;
}
When you want to play corresponding music, you could do like this
public void play(MediaPlayer mediaPlayer, Context context, String musicName) throws IOException {
AssetFileDescriptor assetFileDescriptor = context.getAssets().openFd(musicName);
mediaPlayer.setDataSource(assetFileDescriptor.getFileDescriptor(),
assetFileDescriptor.getStartOffset(),
assetFileDescriptor.getLength());
mediaPlayer.prepare();
mediaPlayer.start();
}
Hope this will solve your problem .
Right click on res folder and Create new folder called raw. Now copy paste few .MP3 files inside it. Check those links for better understanding.
link1
link2
From Assest folder
public void playBeep() {
try {
if (mp.isPlaying()) {
mp.stop();
mp.release();
mp = new MediaPlayer();
}
AssetFileDescriptor descriptor = getAssets().openFd("mysong.mp3");
mp.setDataSource(descriptor.getFileDescriptor(), descriptor.getStartOffset(), descriptor.getLength());
descriptor.close();
mp.prepare();
mp.setVolume(1f, 1f);
mp.setLooping(true);
mp.start();
} catch (Exception e) {
e.printStackTrace();
}
}
You can read file from asset using AssetManager
AssetManager assetManager = getAssets();
String[] files = assetManager.list("");
Note that this file is String array. So don't forget to initialize new file for each element of the array before iterating over it.

How do I copy string from text file to Java string?

I've looked through the other threads on here and can't find anything that works for me. What I need to do is read a text file from the external storage and copy the text to a string in my Java file. After it gets converted I need it to compare that string to one typed in by the user in an Edittext. This is what I have so far and I'm sure there's a lot wrong with it.
try {
decrypt();
} catch (IOException e) {
e.printStackTrace();
} catch (NoSuchAlgorithmException e) {
e.printStackTrace();
} catch (NoSuchPaddingException e) {
e.printStackTrace();
} catch (InvalidKeyException e) {
e.printStackTrace();
}
final EditText pin = (EditText) findViewById(R.id.pin);
pin.setOnKeyListener(new View.OnKeyListener() {
public boolean onKey(View v, int keyCode, KeyEvent event) {
if ((event.getAction() == KeyEvent.ACTION_DOWN) &&
(keyCode == KeyEvent.KEYCODE_ENTER)) {
File file = new File(Environment.getExternalStorageDirectory().toString() + "/Vault/data1.txt");
String pinkey = pin.getText().toString();
if (pinkey.matches("")) {
Toast.makeText(MainActivity.this, "Type in pin", Toast.LENGTH_LONG).show();
}
else {
try {
decrypt();
} catch (IOException e) {
e.printStackTrace();
} catch (NoSuchAlgorithmException e) {
e.printStackTrace();
} catch (NoSuchPaddingException e) {
e.printStackTrace();
} catch (InvalidKeyException e) {
e.printStackTrace();
}
StringBuilder text = new StringBuilder();
String key = new String(file.toString());
try {
BufferedReader br = new BufferedReader(new FileReader(file));
String line;
while ((line = br.readLine()) != null) {
text.append(line);
}
br.close();
} catch (IOException e) {
e.printStackTrace();
}
if (file.exists()) {
} else {
showHelp(null);
}
if (pinkey.equals(br)) {
Toast.makeText(MainActivity.this, "You're signed in", Toast.LENGTH_SHORT).show();
}
else {
Toast.makeText(MainActivity.this, "Try again", Toast.LENGTH_LONG).show();
}
}
return true;
}
return false;
}
Any help is appreciated!
Silly me. I should probably use the scroll bar before commenting :p
Anyways, try your try block like this
BufferedReader br = new BufferedReader(new FileReader(file));
try {
StringBuilder sb = new StringBuilder();
String line = br.readLine();
while (line != null) {
sb.append(line);
sb.append(System.lineSeparator());
line = br.readLine();
}
String fileAsString = sb.toString();
} finally {
br.close();
}
Not sure if you need a new line separator, but if your comparing it to another file it might be good to get it in a form that represents a file...I'd assume.
You can use a simple Scanner and File objects:
public String readFile(String path) {
try {
Scanner se = new Scanner(new File(path));
String txt = "";
while (se.hasNext())
txt += se.nextLine() + "\n";
se.close();
return txt;
} catch (FileNotFoundException e) {
return null;
}
}
You open a scanner that scans the file, and as long as there is more to read from the file, you append the next line to a string.
This method returns null if the file doesn't exist, and an empty string if the file is empty.

Android - saving Int on Internal Storage error

I am trying to save an int (score) on the Internal storage of a real device, and for some reason, when I load it, it makes score equals to 0.
Code:
public int score;
String scoreString = Integer.toString(score);
FileOutputStream fileOutputStream = null;
FileInputStream fileInputStream = null;
final TextView best = (TextView) findViewById(R.id.best);
// Save
try {
file = getFilesDir();
fileOutputStream = openFileOutput("record.txt", Context.MODE_PRIVATE);
fileOutputStream.write(scoreString.getBytes());
} catch (FileNotFoundException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}finally {
if (fileOutputStream != null) {
try {
fileOutputStream.close();
} catch (IOException e) {
e.printStackTrace();
}
}
}
Toast.makeText(MainActivity.this, "Save() works fine " + scoreString + file, Toast.LENGTH_SHORT).show();
// load
try {
FileInputStream fileInputStream = openFileInput("record.txt");
int read = -1;
StringBuffer buffer = new StringBuffer();
while ((read = fileInputStream.read()) != -1){
buffer.append((char)read);
}
Log.i("ELY", buffer.toString());
String record = buffer.substring(0);
best.setText("Best: " + record);
Toast.makeText(MainActivity.this, "Load() OK " + record , Toast.LENGTH_SHORT).show();
} catch (FileNotFoundException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
} finally {
if (fileInputStream != null) {
try {
fileInputStream.close();
} catch (IOException e) {
e.printStackTrace();
}
}
}
Can somebody help me? Thanks
UPDATED Well If you just want to save score you can use SharedPrefernces
To get Score:
public int getScore() {
SharedPreferences pref = getApplicationContext().getSharedPreferences("MY_PREFS", context.MODE_PRIVATE);
return pref.getInt("SCORE", 0);
}
To store Score:
public void setScore(int score) {
SharedPreferences pref = getApplicationContext().getSharedPreferences("MY_PREFS", context.MODE_PRIVATE);
SharedPreferences.Editor editor = pref.edit();
editor.putInt("SCORE", score);
editor.commit();
}

Comparing txt file with input String in Android

I have created a txt file and saved it in the file Explorer at data/data/com.xxx/files/mynote/txt when I entered a string into edit text and click the button.
I want compare txt file content and input String. In my txt file, only minimum length 5 to 6 is stored. How do I do this? I have tried but it can not compare properly - it goes to else block part when I entered the same string as i save in my txt file like "tazin".
Here is my code.
btnSubmitCode=(Button)findViewById(R.id.button_Submit);
btnSubmitCode.setOnClickListener(new OnClickListener() {
#Override
public void onClick(View arg0) {
// TODO Auto-generated method stub
if(editText_Code.getText().toString().isEmpty())
{
Toast.makeText(getApplicationContext(),"Please Enter Code", Toast.LENGTH_SHORT).show();
}
else
{
String strCode = editText_Code.getText().toString().trim();
create_File(strCode);
readFile();
}
String temp;
String searchString = "tazin";
try {
File file=new File("/data/data/com.xxxxx/files/mynote.txt/");
BufferedReader in = new BufferedReader(new FileReader(file));
while (in.readLine() != null)
{
temp = in.readLine();
System.out.println("String from txt file ="+temp);
if(searchString.equals(temp))
{
System.out.println("word is match");
in.close();
return;
}
else
{
System.out.println("word is not match");
}
}
in.close();
}
catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
});
//Write File
private void create_File(String strtext)
{
FileOutputStream fos = null;
try
{
fos = openFileOutput("mynote.txt", MODE_PRIVATE);
fos.write(strtext.getBytes());
Toast.makeText(getApplicationContext(), "File created succesfully",
Toast.LENGTH_SHORT).show();
}
catch(FileNotFoundException fexception)
{
fexception.printStackTrace();
}
catch(IOException ioexception)
{
ioexception.printStackTrace();
}
finally
{
if (fos != null)
{
try
{
// drain the stream
fos.flush();
fos.close();
}
catch (IOException e)
{
// TODO Auto-generated catch block
e.printStackTrace();
}
}
}
}
//Read File
private void readFile()
{
FileInputStream fis;
try
{
fis = openFileInput("mynote.txt");
byte[] reader = new byte[fis.available()];
while (fis.read(reader) != -1)
{
}
textView_ReadCode.setText(new String(reader));
strReadFile = new String(reader);
System.out.println("Read File Into String Format " + strReadFile);
Toast.makeText(getApplicationContext(), "File read succesfully",
Toast.LENGTH_SHORT).show();
if (fis != null)
{
fis.close();
}
}
catch (FileNotFoundException e)
{
// TODO Auto-generated catch block
e.printStackTrace();
}
catch (IOException e)
{
Log.e("Read File", e.getLocalizedMessage());
}
}
You're misusing the BufferedReader.readLine() method. You're calling it twice each time through your while loop; once in the while conditional, and once in the loop block itself. So, when you do temp = in.readLine() and then the searchString.equals(temp) comparison, you've already skipped a line from the text file. Structure your loop like so:
temp = in.readLine();
while (temp != null)
{
System.out.println("String from txt file =" + temp);
if(searchString.equals(temp))
{
System.out.println("word is match");
in.close();
return;
}
else
{
System.out.println("word is not match");
}
temp = in.readLine();
}
Edit:
Per our chat in comments, here is the updated code for what you need:
btnSubmitCode.setOnClickListener(new OnClickListener()
{
#Override
public void onClick(View arg0)
{
String str = editText_Code.getText().toString();
if(str == null || str.equals(""))
{
Toast.makeText(getApplicationContext(), "Please Enter Code", Toast.LENGTH_SHORT).show();
}
else
{
String strCode = str.trim();
if(checkCode(strCode))
{
System.out.println("word is match");
}
else
{
System.out.println("word is not match");
}
}
}
}
);
...
...
// Returns true if the code has already been used
// Returns false if the code is new
// Creates mynote.txt if it doesn't exist
// Appends code if it is new
private boolean checkCode(String code)
{
String temp;
File file = new File(getFilesDir() + "mynote.txt");
if(file.exists())
{
try
{
BufferedReader in = new BufferedReader(new FileReader(file));
temp = in.readLine();
while (temp != null)
{
if(code.equals(temp))
{
// Match was found
// Clean up and return true
in.close();
return true;
}
temp = in.readLine();
}
in.close();
}
catch (FileNotFoundException e)
{
}
catch (IOException e)
{
}
}
// Match was not found or File doesn't exist
// Append code to mynote.txt and return false
try
{
BufferedWriter out = new BufferedWriter(new FileWriter(file, true));
out.newLine();
out.write(code);
out.close();
}
catch (IOException e)
{
}
return false;
}
In your question you wrote different path then you write in your code so just check your path of file.

Categories

Resources